Почему следующие два шаблона несовместимы и не могут быть перегружены?
#include <vector>
template<typename T>
auto f(T t) { return t.size(); }
template<typename T>
auto f(T t) { return t.foobar(); }
int main() {
f(std::vector<int>());
}
Я думаю, что они (более или менее) эквивалентны следующему, который компилируется отлично (поскольку мы не можем сделать decltype auto(t.size())
, я не могу дать точный эквивалент без какого-либо шума..).
template<typename T>
auto f(T t) -> decltype(t.size() /* plus some decay */) { return t.size(); }
template<typename T>
auto f(T t) -> decltype(t.foobar() /* plus some decay */) { return t.foobar(); }
Clang и GCC жалуются main.cpp:6:16: error: redefinition of 'f'
, если я не могу оставить возвращаемый тип.
(Обратите внимание, что это вопрос rationale. Я не ищу место в Стандарте, которое определяет это поведение, которое вы можете включить в свой ответ, если хотите, но для объяснения почему это поведение желательно или статус-кво).