'Mixing constrained auto placeholder as non-trailing return type and explicit trailing return type
Can we mix constrained auto placeholder as non-trailing return type and trailing return type?
template<class T>
concept C = sizeof(T) > sizeof(char);
C auto g1(auto) -> int { return 1; }
C auto g2(auto) -> char { return '2'; }
int main() {
return g1(0) + g2(0);
}
- GCC & MSVC: ok, returns
1 + '2', even ifg2returns achar - Clang: error with
function with trailing return type must specify return type 'auto', not 'C auto'
I was expecting that
Concept auto foo(auto a, auto b) -> decltype(a + b)
{ return a + b; }
is equivalent to
auto foo(auto a, auto b) -> decltype(a + b)
requires Concept<decltype(a + b)>
{ return a + b; }
Solution 1:[1]
They are not equivalent. First of all, correctly:
auto foo(auto a, auto b) -> Concept decltype(a + b) // or Concept auto
{ return a + b; }
it defines a foo function, which returns the type decltype(a + b), which is constrained by Concept. If it cannot, you get a compile time error.
The other:
auto foo(auto a, auto b) -> decltype(a + b)
requires Concept<decltype(a + b)>
{ return a + b; }
will return a type of decltype(a + b), but this FUNCTION (not the retun type) is constrained to be valid only if decltype(a + b) fulfills the Concept, so if it doesn't you won't get any errors, since this function is cannot be used at all due to the requires clause.
For the 'Mixing' part of the question:
With C auto g1(auto) -> int { return 1; }, you say something like "g1 will return some deduced type (auto) which must fulfill the C concept, and then you say return int. It is kinda weird. So you tell the compiler to deduce the type, then you explicitly say what type to return. I think it makes no sense...
Also the standard standard say that:
"If the function declarator includes a trailing-return-type ([dcl.fct]), that trailing-return-type specifies the declared return type of the function."
I don't find anything if the standard does not allow the C auto at the begining, but it explicitly defines that if you have a trailing-return type, the trailing-return type specifies the returned type, and not the placeholder auto.
So in GCC and MSVC it could be a bug, or they simply ignores that intentionally...
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 |
