tags:

views:

758

answers:

4

Using C++ and the STL, does anybody know how to store integer arrays as nodes in an STL list or vector? I have an unknown number of pairs of numbers that I need to store, and coming from other languages my first thought was to use some sort of list- or vector-like data structure... but I'm running into some trouble. I am 100% sure that I'm making an obvious beginner's C++ mistake, and that somebody who actually knows the language will take one look at what I'm trying to do and be able to set me straight.

So, here's what I've tried. Declaring a list like so works:

stl::list<int[2]> my_list;

And then I can easily make a two-element array, like so:

int foo[2] = {1,2};

This compiles and runs just fine. However, as soon as I try to add foo to my list, like so:

my_list.push_back(foo);

I get a whole gnarly set of compiler errors, none of which I really understand (my C++-fu is almost non-existent):

/usr/include/c++/4.0.0/ext/new_allocator.h: In member function ‘void __gnu_cxx::new_allocator<_Tp>::construct(_Tp*, const _Tp&) [with _Tp = int [2]]’:
/usr/include/c++/4.0.0/bits/stl_list.h:440:   instantiated from ‘std::_List_node<_Tp>* std::list<_Tp, _Alloc>::_M_create_node(const _Tp&) [with _Tp = int [2], _Alloc = std::allocator<int [2]>]’
/usr/include/c++/4.0.0/bits/stl_list.h:1151:   instantiated from ‘void std::list<_Tp, _Alloc>::_M_insert(std::_List_iterator<_Tp>, const _Tp&) [with _Tp = int [2], _Alloc = std::allocator<int [2]>]’
/usr/include/c++/4.0.0/bits/stl_list.h:773:   instantiated from ‘void std::list<_Tp, _Alloc>::push_back(const _Tp&) [with _Tp = int [2], _Alloc = std::allocator<int [2]>]’
test.cpp:5:   instantiated from here
/usr/include/c++/4.0.0/ext/new_allocator.h:104: error: ISO C++ forbids initialization in array new

So, anybody have ideas as to what I'm doing wrong here? Any pointers (no pun intended) would be most helpful. Is it just not possible to store arrays in a std::list? Should I be using a struct? Am I just missing a * or & somewhere?

+13  A: 

The thing stored in a Standard Library container must be assignable and copyable - arrays are neither. Your best bet is to create a list of std::vector. Alternatively, you can wrap the array in a struct:

struct A {
   int array[2];
};

std::list <A> alist;
anon
+6  A: 

You can't store arrays in STL containers. You'd use a vector of vectors or somesuch for the general case. For your specific case, I'd use a vector of std::pair, like so: std::vector<std::pair<int, int> >. std::pair is a class that has two members, first and second, of whatever type you templatize it to be.

Edit: I originally had it as std::vector<std::pair<int> >, but I wasn't sure if it was overloaded to accept only 1 parameter in the case that both types are the same... a little digging turned up no evidence of this, so I modified it to explicitly state that both first and second are ints.

rmeador
The definition in the standard does not provide a default type for the second type, so you must explicitly provide both types.
David Rodríguez - dribeas
+1  A: 

This is a good situation for using boost::array instead of "classic" C-style arrays. This should work:

std::list<boost::array<int,2> > my_list;
boost::array<int,2> foo={{1,2}};
my_list.push_back(foo);
timday
+4  A: 

I'd suggest you use std::pair to store the values in this case. It is located in
<utility>.

You could store pointers to the arrays in the list but then you would have to deal with all the memory management. Using pair is a lot simpler if pairs of values are all you need.

Samuel Otter