Заменить одномерный массив на двумерный
По сути же используется двумерный массив a размером n на m, или же что-то не правильно понимаю? Если же это одномерный, то можете, пожалуйста, подправить, как тогда надо исправить код?
#include <stdio.h>
int main()
{
int * a, i, j, n, m;
scanf("%d",&n);
scanf("%d",&m);
a = (int *) malloc(n*m * sizeof(int));
if (a==NULL)
{
printf("error");
return 1;
}
for (i=0; i<n; i++)
for (j=0; j<m; j++)
scanf("%d", (a + i*m + j));
for (j=m-1; j>=0; j--)
for (i=n-1; i>=0; i--)
if (*(a+i*m+j) < 0)
{
*(a+i*m+j)=0;
break;
}
for (i=0; i<n; i++)
{
for (j=0; j<m; j++)
printf("%d\t", *(a+i*m+j));
printf("\n");
}
free(a);
return 0;
}
Ответы (2 шт):
a =(int**)malloc(n*sizeof(int*));
for(int i = 0; i<n; ++i){
a[i] = (int*)malloc(m * sizeof(int);
}
//Something...
//
for (int i = 0; i < n; i++){
free(a[i]);
}
free(a);
Так, начнем с того, что у вас одномерный массив n*m, но в примере (вашем) работаете как бы с двумерной матрицей. Обращение к элементам массива у вас осуществляется a+i*m+j,где a - указатель на массив, i - индекс 1 цикла,внешнего;m - количество columns;j - индекс 2 цикла, вложенного. Другими словами, "достучаться" до элемента, как в двумерном массиве путем a[i][j] - неправильно(выдаст ошибку).
Двумерные массивы можно создавать разными способами, они могут иметь разное представление в памяти, с разным способом доступа и почему-то все программисты называют их одним синонимом - матрицей.
Вы реализовали свою матрицу с индивидуальной функцией доступа. Где адрес каждого элемента вычисляется по секретной формуле.
Допустим вы создали матрицу 2x3 и она расположена в памяти так :
00 : [0][0]
01 : [0][1]
02 : [0][2]
03 : [1][0]
04 : [1][1]
05 : [1][2]
тогда ваша формула доступа *(a+i*3+j) будет работать.
Эта формула идентична к представлении матрицы в языке Си и можно сделать так, чтобы формула вычисления элемента была спрятана компилятором. Нужно сделать тип матрицы с фиксированной размерностью.
scanf("%d",&n);
scanf("%d",&m);
typedef int tmNM [ n ] [ m ] ;
и выделить память под неё
tmNM * a = malloc(sizeof(tmNM));
здесь a - будет указателем на тип матрицы с фиксированными размерностями и доступ к элементам будет автоматическим вот так :
( * a ) [ i ] [ j ]
в памяти будет представляться аналогично к вашей программе.
Освобождение памяти :
free ( a ) ;
Другой способ создании матрицы вызван с неудобством передачи типа указателя на матрицу другим функциям. И тогда создают массив указателей на массивы чисел и называют так-же матрицей.
int * * a ;
a = malloc (sizeof( int * ) * n) ;
for(int i = 0;i<n;++i)
a[i] = malloc(sizeof( int ) * m);
a - будет вектором указателей и доступ к a[i] будет иметь значение указателю на массив, который будет выполнять роль строки матрицы.
a[0] == & [0][0]
a[1] == & [1][0]
и доступ к элементам будет выглядеть так :
a[i][j]
& a[i][j] == & a[i][0] + j
Освобождение памяти :
for(int i = 0;i<n;++i)
free ( a[i] );
free ( a ) ;