7

I am attempting to convert a 2D array to 1D. I'm extremely new to C/C++ but I think it's very important to learn how to convert a 2D array to 1D. So here I am stumbling upon this problem.

My code so far is http://ideone.com/zvjKwP

#include<iostream>

using namespace std;

int main()
{

int n=0,m=0; // 2D array nRow, nCol
int a[n][m];
int i,j; // цикъл въвеждане 2D
int q,p,t; // for 2D=>1D
int b[100];
int r; // for cout
cout<<"Enter the array's number of rows and columns: ";
cin>>n>>m;

// entering values for the 2D array
    for (i = 0;i<=n;i++)
    {
        for (j = 0;j<=m;j++)
        {
            cout<<"a["<<i<<"]["<<j<<"]="<<endl;
            cin>>a[i][j];
            cin.ignore();
        }
    }

  // Most likely the failzone IMO
  for (q = 0;q<=i;q++)
    {
        for (t = 0;t<=i*j+j;t++)
        {
            b[t] = a[i][j];
        }
    }
    // attempting to print the 1D values
     cout<<"The values in the array are"<<"\n";
    for(r=0;r<=t;r++)
    {
        cout<<"b["<<r<<"] = "<<b[r]<<endl;
    }

    cin.get();
    return 0;
    }

I wrote a comment at where I think I fail.

I must also limit the numbers that get into the 1D to numbers who's value^2 is greater than 50. But for sure I must solve the problem with the conversion 2D=>1D Can you help me out?

Anton Antonov
  • 1,217
  • 2
  • 14
  • 21

6 Answers6

7

You are right with your supposition:

The cycle should be like:

for (q = 0; q < n; q++)
{
    for (t = 0; t < m; t++)
    {
        b[q * m + t] = a[q][t];
    }
}

It is always easier to consider such conversions from the view point of the higher dimension array. Furthermore with your code you did not actually modify i or j in the b assigning cycle, so you should not expect different values to be assigned to the different array members of b.

Wyck
  • 10,311
  • 6
  • 39
  • 60
Boris Strandjev
  • 46,145
  • 15
  • 108
  • 135
5

http://www.cplusplus.com/doc/tutorial/arrays/

In that link look at the section on pseudo-multidimensional arrays.

I've seen many examples that that get the subscripting algorithm wrong. If in doubt, trace it out. The order of sub-scripting a 2D array should go sequentially from 0-(HEIGHT*WIDTH-1)

#define WIDTH 5
#define HEIGHT 3

int jimmy [HEIGHT * WIDTH];
int n,m;

int main ()
{
  for (n=0; n<HEIGHT; n++)
    for (m=0; m<WIDTH; m++)
    {
      jimmy[n*WIDTH+m]=(n+1)*(m+1);
    }
}
spellmansamnesty
  • 469
  • 4
  • 10
3

First of all, the size of the 1D array should be n*m.

The cycle can be as follows-

int lim = n*m;

for(q = 0; q<lim; ++q) {

    b[q] = a[q/m][q%m];
}
Shubham
  • 935
  • 1
  • 7
  • 25
3

You can also do it this way;

int singleArraySize = columns * rows;
for (int i = 0; i < singleArraySize; ++i)
    *(oneDArr + i) = *(twoDArr + i);

the second example is taking advantage of fact that 2D array occupies consecutive spaces.

So if you have array[3][3] = {{1,2,3}, {4,5,6}, {7,8,9}} in computer memory the are stored like this:

memory address | array[i][j] | value
---------------+-------------+---------
0x1            | array[0][0] | 1
0x2            | array[0][1] | 2
0x3            | array[0][2] | 3
0x4            | array[1][0] | 4
0x5            | array[1][1] | 5
0x6            | array[1][2] | 6
0x7            | array[2][0] | 7
0x8            | array[2][1] | 8
0x9            | array[2][2] | 9

where memory address is address where value is stored.

1

This code

int n=0,m=0; // 2D array nRow, nCol
int a[n][m];

is invalid. First of all the dimensions shall be constant expressions and there is no sense to set them to 0.

And the more simple way to do your task is to use a pointer. For example

int *p = b;

for ( const auto &row : a )
{
    for ( int x : row ) *p++ = x;
}
Vlad from Moscow
  • 301,070
  • 26
  • 186
  • 335
  • 1
    I think I'm not so familiar with C++ to understand this code at 100%. Sorry! :D – Anton Antonov Nov 11 '13 at 19:05
  • There is nothing difficult. It is so-called the range-based for statement that you should learn. You can substitute it for your loops but preserve the idea to use pointer as the destination variable – Vlad from Moscow Nov 11 '13 at 19:07
0

This answer uses the C utility memcpy. Since memory is contiguous, you can copy it as a block of bytes:

#include <string.h> // For memcpy
#include <iostream>

int main() {
    // Fill in the 2D array with some values...
    int a[3][3] = {{1,2,3},{4,5,6},{7,8,9}};

    // Allocate the 1D array
    int b[3*3];

    // Copy into 1D array
    memcpy(b,a,9*sizeof(int));

    // Print the result
    for (int i(0); i<9; ++i) {
        std::cout << b[i] << " ";
    }
}

Output:

1 2 3 4 5 6 7 8 9
thayne
  • 426
  • 5
  • 18