2

I have used stackoverflow for a long time and never had to post a question before, but this one has me EXTREMELY frustrated.

I have this piece of code

array<array<string, 10>, 10> cShots = 
{
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " }
}; 

outside of any methods at a global level. What I'm trying to do is create a 2d array 10 by 10 full of blank space strings. What happens instead is that I get an error on the first bracket of the third line saying "too many initializer values". Every solution I have found to this error says that what I am doing is correct. I have tried doing it multiple other ways.

string** cShots = 
{
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "}
}; 

string cShots[10][10] = 
{
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "},
    {" ", " ", " ", " ", " ", " ", " ", " ", " ", " "}
}; 

but everything I try has the same result.

PLEASE HELP!

EDIT: well...I figured out that I just needed more brackets...and the error went away...but now when I run my code visual studio says that it was a successful build, but then freezes forever...

  • 1
    If I recall correctly you need to wrap the outermost layer in one more pair of braces to pass the inner arrays to the constructor. See this: http://coliru.stacked-crooked.com/a/4c57a7193629931f and for an alternative syntax http://coliru.stacked-crooked.com/a/eb5b620cb4146d4a – shuttle87 Nov 11 '15 at 18:37
  • Also what compiler are you using and what compilation flags? – shuttle87 Nov 11 '15 at 18:43
  • I'm working in visual studio express 2015. – TheMartyred Nov 11 '15 at 18:50
  • I added the brackets and the error went away. the problem now is that whenever i try to use the local windows debugger on it, visual studio just freezes. – TheMartyred Nov 11 '15 at 18:51
  • Maybe file a bug report if this causes a crash. – shuttle87 Nov 11 '15 at 19:34

1 Answers1

3

Things are a little easier to understand when you see that there is a special case for the syntax here. std::array is an aggregate, it's a struct that contains a single data member which is the underlying raw array. To initialize one of these you need to uniform-initialize the array (first braces) then initialize the underlying raw array member stored in the std::array (second braces);

So when you have something such as:

array<string, 3> test = {{"a", "b", "c"}};

The outermost braces initialize the array itself then the inner part initializes the underlying array. In this case it's clear that this is the way it is working and a special case was made (See the standard: section 8.5 for more) that allows the compiler to accept the other syntax of:

array<string, 3> test = {"a", "b", "c"} ;

However in the case of the question it's not of the special-case-form specified in the standard so you need the extra braces (this too caused me confusion when I first encountered it). There is a defect report about this actually http://www.open-std.org/JTC1/SC22/WG21/docs/papers/2012/n3367.html#1270

In more recent c++ standards (see Can we omit the double-braces for std::array in C++14?) this requirement is relaxed.

Because the code in the question does not benefit for the special case of the syntax we need both braces. In this case your initializer is however not of length one:

array<array<string, 10>, 10> cShots = 
{
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " }, //extra initializer elements but only one underlying raw array
    //snip
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " }
}; 

To the compiler it looks like you are trying to initialize multiple members of the std::array class but the problem is that there is only one underlying storage array. Hence the compiler error message you get here. To get this to work you need to be more explicit and add the extra pair of braces to get an initializer of length one passed to the outer std::array. You then initialize the underlying raw array which contains the other arrays:

array<array<string, 10>, 10> cShots = 
{{
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " },
    //snip
    { " ", " ", " ", " ", " ", " ", " ", " ", " ", " " }
}}; 

For a proof of concept see this: http://coliru.stacked-crooked.com/a/4c57a7193629931f (Note the nested arrays here do benefit from the syntatical special case)

Community
  • 1
  • 1
shuttle87
  • 15,466
  • 11
  • 77
  • 106