How can I initialize 2d array with a list of 1d arrays?

前端 未结 4 1803
孤街浪徒
孤街浪徒 2021-01-18 05:21

How can I initialize 2d array with a list of 1d arrays?

void main()
{
    int a[] = { 1,2,3 };
    int b[] = { 4,5,6 };
    int array[][3] = { a,b };
}


        
相关标签:
4条回答
  • 2021-01-18 05:29

    Use std::array.

    auto a = std::array{ 1,2,3 };
    auto b = std::array{ 4,5,6 };
    auto array = std::array{ a,b };
    

    Demo

    0 讨论(0)
  • 2021-01-18 05:38

    std::array is the way to go here, but if you want to stick to the means of the language (and not the standard lib), and your combined array has the same life time as its constituents, and if the data can be shared, you can have an array of pointers to arrays and say

    int a[] { 1,2,3 };
    int b[] { 4,5,6 };
    
    decltype(a) *abArr[] {&a, &b};
    // equivalent to 
    // int (*abArr[])[3] { &a, &b };
    

    Note that this is not a 2-dimensional array, and its elements are not integers. But you can still range-loop through both dimensions because the pointers are true pointers to a fixed-size array (as opposed to pointers to a mere int as a result of array decay, which couldn't be range-looped).

    Since the array elements are pointers it is necessary to dereference row:

    for (auto const& row : abArr)
        for (auto const& e : *row)
            cout << e << " ";
    

    Live example: http://coliru.stacked-crooked.com/a/cff8ed0e69ffb436

    0 讨论(0)
  • 2021-01-18 05:40

    raw arrays in C++ are kind of second class citizens. They can't be assigned and they can't be copied, which means you can't use them to initialize other arrays, and their name decays into a pointer in most circumstances.

    Lucky C++11 offers a solution. std::array acts like a raw array, but it doesn't have the drawbacks. You can use those instead to build a 2d array like

    std::array<int, 3> foo = {1,2,3};
    std::array<int, 3> bar = {3,4,5};
    std::array<std::array<int, 3>, 2> baz = {foo, bar};
    

    and if you have C++17 support you can leverage class template argument deduction to get rid of having to specify the template parameters and the code simplifies to

    std::array foo = {1,2,3};
    std::array bar = {3,4,5};
    std::array baz = {foo, bar};
    

    which you can see working in this live example

    0 讨论(0)
  • 2021-01-18 05:40

    The way you presented - not at all... You can have:

    int array[][3] = { { 1, 2, 3 }, { 4, 5, 6 } };
    

    If you still need a and b, you could then have these as pointers:

    int* a = array[0];
    int* b = array[1];
    

    or a bit closer to your original try: References to array:

    int(&a)[3] = array[0];
    int(&b)[3] = array[1];
    

    This way, you could still e. g. apply sizeof to a and b...

    Or the other way round: create an array of pointers

    int a[] = { 1,2,3 };
    int b[] = { 4,5,6 };
    int* array[] = { a, b };
    

    All these solutions presented so far have in common that both a and array[0] access exactly the same data. If you actually want to have two independent copies instead, then there's no way around copying the data from one into the other, e. g. via std::copy.

    If you switch from raw array to std::array, though, you can have this kind of initialisation (with copies) directly:

    std::array<int, 3> a;
    std::array<int, 3> b;
    std::array<std::array<int, 3> 2> array = { a, b };
    
    0 讨论(0)
提交回复
热议问题