1

In std::array, we can simply state like this

std::array<std::array<char,10>, 2> arr_gcc{ 
    "abcdefghi", "abcdefghi"
};

Or even in clang with -Wall, they just need somewhat more explicit expression, having to add some more subobject braces like this

std::array<std::array<char,10>, 2> arr_clang_wall_favor{{
    {"abcdefghi"}, {"abcdefghi"}
}};

When it comes to std::vector, one way is to explicitly construct each subobject like his

// This works in both clang and gcc
std::vector vec{
    std::array<char,10>{"abcdefghi"}, std::array<char,10>{"abcdefghi"}
};

If we try to do in aggregate like this

std::vector<std::array<char,10> > vec_clang{{
    {"abcdefghi"}, {"abcdefghi"}
}};

It works only in clang but is an error in gcc as

<source>: In function 'int main()':
<source>:21:6: error: no matching function for call to 'std::vector<std::array<char, 10>, std::allocator<std::array<char, 10> > >::vector(<brace-enclosed initializer list>)'
     }};
      ^
In file included from /opt/compiler-explorer/gcc-7.3.0/include/c++/7.3.0/vector:64:0,
                 from <source>:2:
/opt/compiler-explorer/gcc-7.3.0/include/c++/7.3.0/bits/stl_vector.h:411:2: note: candidate: template<class _InputIterator, class> std::vector<_Tp, _Alloc>::vector(_InputIterator, _InputIterator, const allocator_type&)
  vector(_InputIterator __first, _InputIterator __last,
  ^~~~~~
/opt/compiler-explorer/gcc-7.3.0/include/c++/7.3.0/bits/stl_vector.h:411:2: note:   template argument deduction/substitution failed:
<source>:21:6: note:   candidate expects 3 arguments, 1 provided
     }};
      ^

Are there aggregate initialization differences between std::vector and std::array? If yes, Why?

By the standard, is gcc supposed to compile that aggregate like clang does?

godbolt.org/g/TRZHnu

sandthorn
  • 2,770
  • 1
  • 15
  • 59

0 Answers0