Open Quuxplusone opened 6 years ago
@rsmith: I have not asked GCC, and don't plan to (although anyone else should feel free to do so).
My original test case (before reducing) made GCC's behavior much more "apparently intuitively correct":
template<int K> struct AA { int a[K/2]; int b[K - K/2]; };
template<int K> struct BB { int a[K - K/2]; int b[K/2]; };
static_assert(is_n_constructible<0, AA<0>>::value == true);
static_assert(is_n_constructible<0, BB<0>>::value == true);
static_assert(is_n_constructible<1, AA<1>>::value == ONLY_ON_GCC);
static_assert(is_n_constructible<1, BB<1>>::value == true);
static_assert(is_n_constructible<2, AA<2>>::value == true);
static_assert(is_n_constructible<2, BB<2>>::value == true);
static_assert(is_n_constructible<3, AA<3>>::value == true);
static_assert(is_n_constructible<3, BB<3>>::value == true);
static_assert(is_n_constructible<4, AA<4>>::value == true);
static_assert(is_n_constructible<4, BB<4>>::value == true);
// ...
Clang is enforcing [dcl.init.aggr]p12 (http://eel.is/c++draft/dcl.init.aggr#12):
If an aggregate class C contains a subaggregate element e with no elements, the initializer-clause for e shall not be omitted from an initializer-list for an object of type C unless the initializer-clauses for all elements of C following e are also omitted.
GCC's behavior here does not seem reasonable nor consistent with the base language to me. Have you asked the GCC folks whether they would consider this to be a bug and might fix it? Example of the inconsistency:
struct A {};
struct B { int n; };
struct X { A a; B b; };
struct Y { int a[0]; int b[1]; };
X{convertible_to_anything{}} // constructs 'a' member via conversion function
Y{convertible_to_anything{}} // constructs 'b' member via conversion function!
Extended Description
Clang believes that an aggregate consisting of a zero-sized array and a 1-sized array is NOT initializable with just one initializer in the curly braces, whereas GCC believes that it IS.
It would be convenient if Clang matched GCC's behavior for zero-sized arrays. The existing behavior is definitely not a "bug bug", as zero-sized arrays are non-standard and I'm not aware that Clang has promised to mimic GCC in this area; but the discrepancy between the two compilers in this area is awkward for testing.