When I try to compile
template<int dim>
struct Foo
{
Foo(const int (&i)[dim]) {}
};
int main()
{
Foo<2> f = Foo<2>((int[2]){0}); // line 9
return 0;
}
I get the compilation error
test.cpp:9:31: error: no matching function for call to ‘Foo<2>::Foo(int [1])’
Apparently, the argument I pass to the constructor is regarded as an int[1]. Why isn’t it regarded as an int[2] (which could then be casted to a const reference as expected by the constructor)? Shouldn’t the missing elements be value-initialized according to 8.5.1 (7)?
After all, replacing line 9 with
int arg[2] = {0};
Foo<2> f = Foo<2>(arg);
lets me compile the program. Additionally, when I try to pass (const int [2]){0, 0, 0} to the constructor, I get the error message too many initializers for ‘const int [2]’, so apparently, the compiler is trying to construct a const int[2].
Somebody please shed some light on this unintuitive behavior.
The construct
(int[2]){0}is a C99 compound literal, which is not part of C++. How particular compilers interpret in the context of C++ is anyone’s guess (or a matter of examining the source code).PS. OK, it seems that gcc 4.7/gcc 4.8/clang-3.1 handle it quite sensibly – the type of the compound literal is the same as the C99 standard specifies it.
I guess the OP compiler is a bit older.