Reputation: 143
I have declared a 2D array in the following way (please note that I'm very beginner!)
double **A=new double*[10];
for(int i=0;i<10;i++)
A[i]=new double[5];
So I guess this already defines a matrix of size 10 by 5.
I know that to refer to its row I can use
A[i]
But the question is, how to refer to a column of A? something like A[][i]?
Upvotes: 2
Views: 10427
Reputation: 195
You cannot access a column directly.
You can either access a row by A[i] (which is an array itself) or an element A[i][j] (which is a single double in your case).
If you want to get a column you have to iterate throw the array
for(unsigned int i = 0; i < 10; i++)
{
A[i][2] // do something
}
Accesses the third column.
So it is useful to think about if you want to create a 10x5 or a 5x10 matrix. If you often need to work with just a row or an column, it may be a good idea to invert the array layout (here switch columns and rows)
EDIT: Here is some simplified explanation: Imagine the following code
int** A = new int*[2];
for(int i=0;i<2;i++)
A[i]=new int[3];
// more init code
Then the array in memory may look like this:
So it is simple to see that the "blue row" can be accessed directly as you have its startaddress in A[0] But if you want every third element of the sub arrays you have to iterate through A and add 2 to every startadress. Especially as there is no guaranteed fixed distance in memory between the subarrays if you use heap memory via "new".
But you often can speedup computations by choosing the layout of your arrays in a good way. One could for example store the second matrix transposed when implementing matrix multiplication.
Upvotes: 4
Reputation: 767
Elements of any row can be referred by arr[row_num][i]
.
Similarly elements of any column can be referred by arr[i][col_num]
.
Note that indexes are zero-based in C/C++. So if your column/row size is x
, i
can vary from 0
to x-1
.
As you are a beginner, i would also like to tell you a bit more about arrays in C/C++. Firstly, i would suggest you to read about pointers if you are not familiar with them.
When you declare an array, say, int arr[10], arr[0] means the first element. Also, arr + 0 (or simply arr) means the address of the first element. Similarly, arr[i] means ith element, arr + i means address of the ith element. To print the value at an address, in c/c++, you can use value-at operator, represented by (*), e.g. *(arr + i) will be equivalent to arr[i], i.e. the ith element. Also, address of operator (&) gives to the address of an element, &arr[i] is equivalent to (arr + i).
If arr is a 2-d array, arr[i][j] means jth element of ith row. arr[i] means address of first element of ith row. c/c++ are row-major, which means first row is filled first and then second and so on. and we have to specify the row size always while declaring a 2-d array.
Note: In pointer-arithmetic, arr+i, and arr+i+1, etc. are not being incremented by 1, but by the size of the element it is pointing to.
So, to refer to a row, we can do the following:
//note that arr[row_num] is an address
int * new_1d_arr = arr[row_num];
for(int i = 0; i < row_size; i++)
cout << new_1d_arr[i] << endl;
Similarly, we can also refer to an column, but it would be a bit more complex, as we will have to increment i, not by 1, but by the row_size, due to the fact that arrays in c/c++ are row-major, and we would have to skip over number of elements (equal to row_size) to get to the next element in the same column.
Upvotes: 1
Reputation: 10852
Enother way using pointers.
// Matrix dimentions
int n_rows = 10;
int n_cols = 5;
// create rows as pointers to columns
double **A = new double*[n_rows];
// create columns
for (int i = 0; i < n_rows; i++)
{
A[i] = new double[n_cols];
}
// Fill our matrix
int count=0;
for (int i = 0; i < n_rows; i++)
{
for (int j = 0; j < n_cols; j++)
{
A[i][j]=count;
++count;
}
}
// Create pointers columns
double ***A_t = new double**[n_cols];
// create matrix pointers rows
for (int i = 0; i < n_cols; i++)
{
A_t[i] = new double*[n_rows];
}
// And fill it with pointers to transposed main matrix elements
for (int i = 0; i < n_rows; i++)
{
for (int j = 0; j < n_cols; j++)
{
A_t[j][i]=&A[i][j];
}
}
// output first row/column for each case
for (int i = 0; i < n_cols; i++)
{
cout << *(A[0]+i) << endl;
}
cout << "-------------"<< endl;
for (int i = 0; i < n_rows; i++)
{
cout << **(A_t[0]+i) << endl;
}
// Work with matrices here
// Don't forget to clean everything.
Upvotes: 2
Reputation: 12846
You cannot refer to a column in this way. This is because you dont really have a matrix, you specified an array of arrays. The arrays are your rows, but the columns are not directly stored. If you want to get a whole column, you have to run through all rows, receive the value stored in that column and store it in a different array.
auto column = new double[10];
for(int i = 0; i < 10; i++){
column[i] = A[i][2] //if you want to get the 2nd column
}
Upvotes: 1
Reputation: 224
Rows and columns are sort of abstracted away, you can consider the spatial orientation to go in either direction if you want (10 columns, or 5 columns if you see what I mean). But obviously you need to keep your use consistent.
It probably makes sense to keep the 'outer' array the column, so that A[x][y] makes sense in a cartesian coordinate type sense. From your example, you want to be indexing like A[i][] (i.e. your i index is the column, or X coordinate).
Upvotes: 1
Reputation: 373
A 2D array looks something like this
if ur 2d array is a[i][j] then i will be ur rows and j will be ur columns.
if u want to access columns of first row you can do something like this a[0][1] a[0][2] a[0][3]
see the link it will clear you more.
https://i.sstatic.net/21Bqr.png
Upvotes: 1