Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I work with nested vectors in C++?

Tags:

c++

vector

I'm trying to work with vectors of vectors of ints for a sudoku puzzle solver I'm writing.

Question 1:

If I'm going to access a my 2d vector by index, do I have to initialize it with the appropriate size first?

For example:

typedef vector<vector<int> > array2d_t;

void readAPuzzle(array2d_t grid)
{
    for(int i = 0; i < 9; i++)
        for(int j = 0; j < 9; j++)
            cin >> grid[i][j];
    return;
}

int main()
{
    array2d_t grid;
    readAPuzzle(grid);
}

Will seg fault. I assume this is because it is trying to access elments of grid that have not yet been initialized?

I've swapped out grid's declaration line with:

array2d_t grid(9, vector<int>(9, 0));

And this seems to get rid of this seg fault. Is this the right way to handle it?

Question 2:

Why is it that when I try to read into my grid from cin, and then print out the grid, the grid is blank?

I'm using the following code to do so:

void printGrid(array2d_t grid)
{
    for (int i = 0; i < 9; i++)
    {
        for (int j = 0; j < 9; j++)
        {
            cout << grid[i][j] + " ";
        }
        cout << endl;
    }
}

void readAPuzzle(array2d_t grid)
{
    for(int i = 0; i < 9; i++)
        for(int j = 0; j < 9; j++)
            cin >> grid[i][j];

    return;
}

int main()
{
    array2d_t grid(9, vector<int>(9, 0));
    printGrid(grid);
    readAPuzzle(grid);
    printGrid(grid);
}

And I attempt to run my program like:

./a.out < sudoku-test

Where sudoku-test is a file containing the following:

3 0 0 0 0 0 0 0 0  
5 8 4 0 0 2 0 3 0  
0 6 0 8 3 0 0 7 5  
0 4 1 0 0 6 0 0 0  
7 9 0 0 2 0 0 5 1  
0 0 0 9 0 0 6 8 0  
9 3 0 0 1 5 0 4 0  
0 2 0 4 0 0 5 1 8  
0 0 0 0 0 0 0 0 6  

The first call to printGrid() gives a blank grid, when instead I should be seeing a 9x9 grid of 0's since that is how I initialized it. The second call should contain the grid above. However, both times it is blank.

Can anyone shed some light on this?

like image 798
Salaban Avatar asked Feb 27 '10 22:02

Salaban


1 Answers

Q1: Yes, that is the correct way to handle it. However, notice that nested vectors are a rather inefficient way to implement a 2D array. One vector and calculating indices by x + y * width is usually a better option.

Q2A: Calculating grid[i][j] + " " does not concatenate two strings (because the left hand side is int, not a string) but instead adds the numeric value to a pointer (the memory address of the first character of the string " "). Use cout << grid[i][j] << " " instead.

Q2B: You are passing the array by value (it gets copied) for readAPuzzle. The the function reads into its local copy, which gets destroyed when the function returns. Pass by reference instead (this avoids making a copy and uses the original instead):

void readAPuzzle(array2d_t& grid)
like image 99
Tronic Avatar answered Oct 02 '22 03:10

Tronic