-1

How to declare a 2D Vector with following specifications:

  1. Should have 3 columns (Ofcourse not actually but still)

  2. Number of rows undeclared

Some suggest i should wrap an array inside a vector as below:

                typedef array <float, 3> Point
                vector <Point> 2DVector

But is there a way to use only vector to obtain the desired 2D Vector?

leppie
  • 115,091
  • 17
  • 196
  • 297
  • A vector of vectors? A vector containing a `struct`? Or do you mean you want to use only a single vector and no other data-structures or containers? – Some programmer dude Jan 20 '14 at 06:32
  • @Joachim. Yes vector of vector. Yes I want to use only vector. – deepak09027 Jan 20 '14 at 06:35
  • So use a vector of vectors (although the array solution seems better to me). Are you having a particular problem with that? – juanchopanza Jan 20 '14 at 06:38
  • @deepak09027 okay thanks, I'm just going to make sure i understand you correctly before i try post an answer, when you say it should have 3 columns do you mean it must only have 3 columns or would it be a solution if rows and columns could be of any length? (and you just use 3 columns) and would you be comfortable with using an `initializer_list` inside the vector? – James Jan 20 '14 at 07:59
  • @James. It should just "use" three columns. I do not have problem with initializer_list. – deepak09027 Jan 20 '14 at 08:18
  • @juanchopanza. The reason I am not able to use array wrapped inside a vector is: I need to return that vector to a function and the compiler doesn't seem to understand what is "vector>". It is throwing error. Do you know how should I return an array wrapped inside a vector? – deepak09027 Jan 20 '14 at 08:24
  • -1 The question is missing important details, like the reason behind this question and the compiler errors. Please correct. – Antonio Jan 20 '14 at 08:47

2 Answers2

1

How to declare a 2D Vector with following specifications: [...]

A mix of std::vector and std::array is perfectly fine for the requirements:

using table = std::vector<std::array<float, 3>>;
table 2d_vector;

But is there a way to use only vector to obtain the desired 2D Vector?

Here it is:

using table = std::vector<std::vector<float>>;
table 2d_vector;

You'll have to be sure to only add 3 floats to the inner vectors though.


I need to return that vector to a function and the compiler doesn't seem to understand what is vector<array<float>>

Well, yes, of course it does not. std::vector<std::array<float>> does not name a type. You probably meant:

std::vector<std::array<float, 3>>;
//                          ^^^
Shoe
  • 74,840
  • 36
  • 166
  • 272
  • I am writing "using namespace std" before declaring the function. Should there still be a problem? – deepak09027 Jan 20 '14 at 10:02
  • @deepak09027, don't use `using namespace std`. Just prefix STL classes/functions/objects with `std::`. – Shoe Jan 20 '14 at 10:03
1

Using an initializer_list could look like this;

First #include <initializer_list>

std::vector<std::initializer_list<float>> vec{ {1,2,3} };
vec.push_back( {4,5,6} ); // add a row

Accessing each element could be done like;

for (auto list: vec){

    for(auto element: list){

        std::cout<< element << " "; // access each element

    }

    std::cout<<"\n";
}

Getting at an individual element with (x, y) coords;

// access first row (y coord = 0), second element (x coord = 1, also the column)
std::cout<< "vec[0].begin() + 1 = (addr:" << (vec[0].begin() + 1)
         << " - value: " << *(vec[0].begin() + 1) << ')';

All of that together would output;

1 2 3
4 5 6
vec[0].begin() + 1 = (addr:0x40a0d4 - value: 2)

A cleaner way could be done like this;

// using a variable type of initializer_list
std::initializer_list<float> row = {1,2,3};
std::vector<std::initializer_list<float>> vec{ row };

row = {4,5,6}; // change list

vec.push_back(row); // add rows
vec.push_back({7,8,9});

for (auto list: vec){

    for(auto value: list){

        std::cout<< value <<" ";

    }

    std::cout<<"\n";
}

//access without looping
const float *element = vec[0].begin(); 
// pointer to first row, first element (value: 1)

element+=3;
// point to second row, first element (value: 4)

std::cout<<"\nElement("<<*element<<")\n";

// access the same element with x,y coords = (0,1)
int x = 0, y = 1;
std::cout<<"\ncoord(0,1) = "<< *(vec[y].begin() + x) << "\n";

Would output;

1 2 3
4 5 6
7 8 9

Element(4)

coord(0,1) = 4

Problems i can think of with this (assuming it's of any worth) are that;

1) the data is initialized as constant floats and as far as i know you cannot change them.
and
2) if you change the list to equal {0,1,2,3,4,5} you now have more than 3 columns.

James
  • 1,009
  • 10
  • 11
  • Thanx for the input. I don't want the data to be initialized as constant floats and later restriction of not be able to change them. But it was informative. Thanx. – deepak09027 Jan 20 '14 at 10:01
  • No worries, if you ever need a constant 2d vector you might think of this :) – James Jan 20 '14 at 12:45