How to use a "vector of vector"? - c++

I already searched on the web for it but I didn't get satisfying results.
I want to create something like
vector< vector<int*> > test_vector;
How do i fill this vector of vector? How to access it's members? Maybe someone knows some nice tutorials on the web?
kind regards
mikey

Just remember that each element of test_vector is of type vector<int*>. You would fill test_vector by filling each element vector.
You can access this just like any multi-dimensional array. See:
int *p = test_vector[0][0];
Or:
int *p = test_vector.at(0).at(0);

A question similar to yours was posted at DreamInCode: http://www.dreamincode.net/forums/topic/37527-vector-of-vectors/

You fill a vector of vectors by putting vectors in it.
You access its members the same way you would any other vector.

PS
If you want to use some kind of a matrix, I would prefer to use only one dimensional vector and map the access (because of performance).
For example Matrix M with m rows and n columns: you can map call
M[i][j] = x to M[i*n+j] = x.

Related

Does an array of vectors form a 2D vector?

Does the following statements form a 2D vector?
Also mention the dimensions of the vector if it does. Is there another way of declaring a global 2D vector?
Statements:
vector<int> *adj;
adj = new vector<int>[number_of_nodes];
The above statements have been used for declaration of a global adjacency matrix for a graph.
It seems the question isn't clear to much of you. I want to declare a global adjacency list using vectors such that I can use direct addition of edges in graph like v[a].push_back(b). For that, I have to specify first dimension of vector while declaring which I don't have until the main is executed.
No, but it gives similar behaviour. So what you have created is a pointer to an array of vectors. So you will end up with this:
adj[0] = []
adj[1] = []
...
adj[number_nodes] = []
and doing a push_back is a legitimate way to add to the vectors:
adj[0].push_back(some_num) --> adj[0] = [some_num]
But this is a terrible way to approach this! Why?
You are using raw memory that you will have to manage and make sure you delete.
You cant use any of the awesome std::vector functionality on the first dimension of the matrix.
There is no good way to figure out the size of the vector unless you know about the variable number_of_nodes.
... A long list, but you get it.
You can already see that a std::vector can be used as a 1D matrix. So use 2 vectors:
std::vector<std::vector<int>> Matrix2D;
If you need an initial size in some dimension then you can do this:
std::vector<std::vector<int>> Matrix2D(number_of_nodes, std::vector<int>());
Or this:
Matrix2D.resize(number_of_nodes);
Or if that size is fixed at compile time then you could even do this:
const int number_of_nodes = 10;
std::array<std::vector<int>, number_of_nodes> Matrix2D;
Or go extra big and get a library for Matrix use like Eigen.

Cannot access element of 2d heap vector using operator[]

I have a 2d vector that needs to be allocated on the heap and am using the below line of code to declare and size it.
vector<vector<double>> *myArray = new vector<vector<double>>(x, vector<double>(y));
where x and y are the number of rows and columns respectively.
When I try to access an element of the vector using myArray[0][0] = 3.0;, I get the following error,
error: no viable overloaded '='
myArray[0][0] = 3.0;
I would appreciate any help in figuring this out.
Notes:
The number of rows and columns needs to be dynamic, hence myArray is on the heap.
The array needs to be resizable, which is why I am using std::vector.
I understand that I can create a vector of vectors (number of rows) and then in a for-loop resize each row element to the required number of columns. What I do not understand is why the above code does not work since as far as I know it should perform the same function.
For some strange invalid reason, you are using a pointer to a vector. Since operator[] works with pointers, when you do
myArray[0][0] = 3.0;
you are actually accessing a vector<double>, not a double, because myArray[0] gets you a vector<vector<double>>.
The obvious fix is not to use a pointer in the first place:
vector<vector<double>> myArray(x, vector<double>(y));
must be:
(*dataArray)[0][0] = 3.0

dynamically changing name of an array in c++

Hi I have a problem where at compile time, I don't know how many vectors in my program are needed. The number required depends on a data set given at run-time, which will results in the range of vectors needed to be from 1 to N.
So if the data set requires ten vectors, it will create vec1,vec2,......vecN
How can i dynamically create the vectors so that they all have a different name?
I would then need to call each array separately. Presumably
I could just use strings and a few loops for this.
You can't do that directly. However, you could use a map to store a vector name, and the vector itself:
map<string, vector<int> > myMap;
You can add elements simply like this (if the element with such key doesn't exist yet):
vector<int> vec;
myMap["vec"] = vec;
If you'll do it with a key that already exists, the value will be replaced. For example:
vector<int> vec;
vector<int> vec1;
myMap["vec"] = vec;
myMap["vec"] = vec1;//now myMap["vec"] holds the vec1 vector
You can also easlly access elements like this:
myMap["vec"]//this will access the vector with the key "vec1"
You can create a vector to contain your vectors:
std::vector<std::vector<int>> my_vector_of_vectors;
// Add a vector
my_vector_of_vectors.push_back(std::vector<int>{});
// Add a number to the inner vector
my_vector_of_vectors[0].push_back(1);
you have a vector of vectors, vec[0] to vec[n], each one containing the vector.
However, this works est if you know the number of vectors (eg 10). If you need to add new ones on-demand, then a list of vectors or a map might be a better option for you.

Multiple indices into a 1D array

I was trying to implement strongly connected algorithms from different sources. I found one that confuses me at http://www.oneous.com/Tutorial-Content.php?id=18
The reason for my confusion is this line:
if (used[v[s][i]] == 0)
DFS(v[s][i]);
We have declared v as a one-dimensional vector, but here it is used as a 2-dimensional vector. I think this is an error but can't figure out how to fix it. Please help me solve this problem.
v is declared as:
vector<int> v[1005];
i.e. an array of vectors. So the first index accesses into the array, the second accesses into the vector.
v is an array of vectors. So v[1] is a vector<int> at position 1, and v[1][2] is an integer at vector<int> position 2.
Vector class allows that because it overrides [] operator

How to access an index in a vector without segfaulting

I know this is simple, so I apologize in advance.
I am segfaulting when trying to access a vector by index. For example...
vector<float> some_vec;
int i = 0;
for (some iterator loop here)
{
//snip
some_vec[i] = some_float;
i++;
}
What am I doing wrong?
After
std::vector<float> some_vec;
your vector is empty. You must not access any element in it then, because there isn't any.
If you want to put values into it, you need to append them to the vector using push_back()
for (some iterator loop here)
{
//snip
some_vec.push_back(some_float);
i++;
}
Alternatively, if you know the size in advance, and if the construction of dummy values in the vector is cheap (as it is for float and other built-ins), you can resize() the vector in advance
some_vec.resize(42);
or create it with the right amount of elements
std::vector<float> some_vec(42);
Given either of the two above, you can then access elements 0..41 in the vector.
call resize() function on your vector and then call push_back() to add elements. After this you can access elements using indexing.
Possibly a problem elsewhere in code we can't see, but mostly likely given you've not called resize(), push_back() or insert() that i is outside of the vector. Use some_vec.at(i) = some_float; to check that i is within the valid range for the vector.
My guess is that your vector is empty. Use push_back(some_float) to add elements to it.