Consider the code below:
#include <array>
struct T
{
T() = delete;
};
int main()
{
std::array<T, 0> a;
a.size();
}
We default initialize a 0-sized array. Since there's no elements, no constructor of T
should be called.
However, Clang still requires T
to be default constructible, while GCC accepts the code above.
Note that if we change the array initialization to:
std::array<T, 0> a{};
Clang accepts it this time.
Does non-default-constructible T
prevent std::array<T, 0>
from being default-constructible?
Since there's no elements, no constructor of T should be called.
Does non-default-constructible T preventstd::array<T, 0>
from being default-constructible?
The standard doesn't specify what layout std::array<T, 0>
should have for us to answer that. The zero sized array specialization is only said to behave as follows:
[array.zero]
1 array shall provide support for the special case N == 0.
2 In the case that N == 0, begin() == end() == unique value. The return value of data() is unspecified.
3 The effect of calling front() or back() for a zero-sized array is undefined.
4 Member function swap() shall have a non-throwing exception specification.
The behavior you note is most probably due to differences in implementation alone.
Thanks to @T.C., as pointed out in his comment, it's addressed in LWG 2157, which is still an open issue as of this writing.
The proposed resolution adds this bullet point (emphasis mine):
The unspecified internal structure of array for this case shall allow initializations like:
array<T, 0> a = { };
and said initializations must be valid even when T is not default-constructible.
So it's clear that the intended behavior is to have std::array<T, 0>
default constructible even when T is not.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With