Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Pushing an array into a vector

Tags:

c++

vector

I've a 2d array, say A[2][3]={{1,2,3},{4,5,6}}; and I want to push it into a 2D vector(vector of vectors). I know you can use two for loops to push the elements one by on on to the first vector and then push that into the another vector which makes it 2d vector but I was wondering if there is any way in C++ to do this in a single loop. For example I want to do something like this:

myvector.pushback(A[1]+3); // where 3 is the size or number of columns in the array.

I understand this is not a correct code but I put this just for understanding purpose. Thanks

like image 216
0x0 Avatar asked Dec 27 '10 20:12

0x0


2 Answers

The new C++0x standard defines initializer_lists which allows you to:

vector<vector<int>> myvector = {{1,2,3},{4,5,6}};

gcc 4.3+ and some other compilers have partial C++0x support. for gcc 4.3+ you could enable c++0x support by adding the flag -std=c++0x

Its not the best way to have your static data represented like that. However, if your compiler vendor supports C++ tr1 then you could do:

#include <tr1/array>  // or #include <array>
...

typedef vector<vector<int> > vector2d;
vector2d myvector;

// initialize the vectors
myvector.push_back(vector<int>());
myvector.push_back(vector<int>());

typedef std::array<std::array<int, 3>, 2> array2d;
array2d array = {{1,2,3},{4,5,6}};
array2d::const_iterator ai = array.begin(), ae = array.end();
for (vector2d::iterator i = myvector.begin(), e = myvector.end()
    ; i != e && ai != ae
    ; i++, a++)
{
    // reserve vector space
    i->reserve(array.size());

    // copy array content to vector
    std::copy(ai.begin(), ai->end(), i->begin());
}
like image 82
langerra.com Avatar answered Nov 14 '22 23:11

langerra.com


This is a little tricky, but you could use template recursion to help you in having the assignment done almost completely at compile-time. I understand that's not exactly what you are looking for, but I think it's worthwhile :-)

Here's the code:

#include <vector>

using namespace std;

typedef vector<vector<int> > vector2d;

template<size_t K, size_t M, size_t N>
struct v_copy {
    static void copy(vector2d& v, int(&a)[M][N])
    {
        v[K - 1].assign(a[K - 1], a[K - 1] + N);
        v_copy<K - 1, M, N>::copy(v, a);
    }
};

template<size_t M, size_t N>
struct v_copy<1, M, N> {
    static void copy(vector2d& v, int(&a)[M][N])
    {
        v[0].assign(a[0], a[0] + N);
    }
};

template<size_t M, size_t N>
void copy_2d(vector2d& v, int(&a)[M][N])
{
    v_copy<M, M, N>::copy(v, a);
}

int main()
{
    int A[2][3] = {{0, 1, 2}, {10, 11, 12}};
    vector2d vector(2);

    copy_2d(vector, A);
}

it needed a struct because in C++ you can't do partial specialization of functions. BTW , compiling it with gcc version 4.5.0, this code produces the same assembly as

vector[1].assign(A[1], A[1] + 3);
vector[0].assign(A[0], A[0] + 3);

It should not be very hard to have it compile with different types of 2-dimensions arrays.

like image 25
Simone Avatar answered Nov 15 '22 00:11

Simone