[英]Printing 2-D array through pointers
我的老師給我解決了一個問題,其中:-
1)用戶將輸入“ n”個三角形。
2)輸入“ n”后,用戶將輸入三角形的邊。
3)我們基本上必須打印這些面(基本上是二維數組的問題)。
這是我對問題的執行:-
# include <stdio.h>
# include <stdlib.h>
# include <stdbool.h>
int main(void)
{
int number_of_triangles; // Takes the value of number of triangles the user will input.
scanf("%d", &number_of_triangles);
int *array;
array = malloc(number_of_triangles * 3 * sizeof(int));
//trying to create a 2D array whose column size is fixed i.e. 3.
int i,j; // Counter variables.
for(i = 0; i < number_of_triangles; i++)
{
for(j = 0; j < 3; j++)
{
scanf("%d", ((array + i) + j)); // Scanning value of sides of triangle.
}
}
for(i = 0; i < number_of_triangles; i++)
{
for(j = 0; j < 3; j++)
{
printf("%d ", (*(array + i) + j));//printing those sides. <-This is the problem statement.
}
printf("\n");
}
return 0;
}
代碼工作正常,但我對下面給出的這一行表示懷疑:-
for(i = 0; i < number_of_triangles; i++)
{
for(j = 0; j < 3; j++)
{
printf("%d ", (*(array + i) + j));
//printing those sides. <-This is the problem statement.
}
printf("\n");
}
如果不是printf("%d ", *(*(array + i) + j))
而不是printf("%d ", (*(array + i) + j))
來獲取邊的值三角形?
如果我把printf("%d ", *(*(array + i) + j))
放進去printf("%d ", *(*(array + i) + j))
我會報錯:
間接需要指針操作數(“ int”無效)。
我在C語言中學到的是,要取消對2-D數組指針的引用,我們必須使用前一種方法,而不是我在代碼中使用的后一種方法。 我要去哪里錯了?
您不能兩次取消引用。 您正在處理一維數組,將其用作2D數組。
array + i
類型為int *
,因此*(array + i)
類型為int
,您不能再次取消引用。
相反,您想使用i
和j
獲得正確的索引。 您想要的索引是i * 3 + j
:
*(array + i * 3 + j)
但是,使用[]
表示法更漂亮,它是等效的:
array[i * 3 + j]
*(*(array + i) + j))
可以在通過數組指針數組構造2D數組時使用,也可以在使用的類型為多維數組時使用。
例如:
int **array;
array = malloc(number_of_triangles * sizeof(int *));
for (int i = 0; i < number_of_triangles; ++i)
array[i] = malloc(3 * sizeof(int));
for (int i = 0; i < number_of_triangles; ++i)
for (int j = 0; j < 3; ++j)
printf("array[%d][%d]: %d\n", i, j, *(*(array + i) + j)));
(我省去了所有檢查分配成功的檢查。如果正在使用此代碼,則必須包括這些檢查。)
請注意,示例的最后一行非常丑陋。 *(*(array + i) + j))
等價於array[i][j]
。 因此可以將其重寫:
printf("array[%d][%d]: %d\n", i, j, array[i][j]);
雙引用的另一種用法是使用多維數組類型。
例如,如果您提前知道三角形的數量:
int array[5][3];
for (int i = 0; i < 5; ++i)
for (int j = 0; j < 3; ++j)
printf("array[%d][%d]: %d\n", i, j, *(*(array + i) + j)));
在這種情況下,我們利用了數組標識符衰減到指向其第一個元素的指針這一事實。 array + i
是第i
個三角形的指針,因此*(array + i)
是int *
類型的左值int *
指向三角形i
的int
數組3。
*(array + i) + j
是一個int *
指向三角形i
的邊j
,因此*(*(array + i) + j))
是該元素的int
類型的左值。
同樣,使用數組表示法更漂亮,將*(*(array + i) + j))
替換為array[i][j]
。
對於初學者,您沒有分配二維數組。 您分配了帶有3 * number_of_triangles
元素的一維數組。
該程序無效,因為在此循環中
for(i = 0; i < number_of_triangles; i++)
{
for(j = 0; j < 3; j++)
{
scanf("%d", ((array + i) + j)); // Scanning value of sides of triangle.
}
}
您正在覆蓋已經輸入的值。
這個表達
((array + i) + j)
等效於表達式
array + ( i + j)
所以array + ( 0 + 1 )
等於array + ( 1 + 0 )
就是說,如果使用索引,則兩個表達式都等於&array[1]
如果您的編譯器支持可變長度數組,則程序看起來像
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
int number_of_triangles; // Takes the value of number of triangles the user will input.
scanf("%d", &number_of_triangles);
int ( *array )[3] = malloc( sizeof( int[number_of_triangles][3] ) );
for ( int ( *p )[3] = array; p != array + number_of_triangles; ++p )
{
for( int *q = *p; q != *p + 3; ++q )
{
scanf( "%d", q ); // Scanning value of sides of triangle.
}
}
for ( int ( *p )[3] = array; p != array + number_of_triangles; ++p )
{
for( int *q = *p; q != *p + 3; ++q )
{
printf( "%d ", *q );
}
putchar( '\n' );
}
free( array );
return 0;
}
您可以將循環也重寫為
for ( int i = 0; i < number_of_triangles; i++ )
{
for( int j = 0; j < 3; j++ )
{
scanf( "%d", *( array + i ) + j ); // Scanning value of sides of triangle.
}
}
for ( int i = 0; i < number_of_triangles; i++ )
{
for( int j = 0; j < 3; j++ )
{
printf( "%d ", *( *( array + i ) + j ) );
}
putchar( '\n' );
}
否則,您必須將一維指針數組分配給一維整數數組。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.