#include <stdio.h>
int main(void)
{
int i, j;
int *p = NULL;
int **arr = NULL;
int arry[4][3] = {{1, 2, 3},
{4, 5, 6},
{7, 8, 9},
{10, 11, 12}};
printf("开始: ");
printf("申请存储行指针的空间: ");
arr = (int **)malloc(4* sizeof(int *));
for (i = 0; i < 4; i++) {
printf("申请二维数组第%d行数据的空间(即arr[%d]行的数据): ", i, i);
arr[i] = (int *)malloc(3 * sizeof(int));
}
printf("按照二维数组方式访问动态申请的arr: ");
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
arr[i][j] = (i * 3) + j + 1;
}
}
printf("直接定义二维数组arry的访问方法: ");
for (i = 0; i < 4; i++) {
printf("%p = %d, %p = %d, %p = %d,",
&(arry[i][0]), arry[i][0],
&(arry[i][1]), arry[i][1],
&(arry[i][2]), arry[i][2]);
}
printf("按照二维数组方式访问动态申请的arr: ");
for (i = 0; i < 4; i++) {
printf("%p = %d, %p = %d, %p = %d,",
&(arr[i][0]), arr[i][0],
&(arr[i][1]), arr[i][1],
&(arr[i][2]), arr[i][2]);
}
printf("arr[i][j]等效访问方式: ");
for (i = 0; i < 4; i++) {
for (j = 0; j < 3; j++) {
// arr存储的是行指针,而*arr存储的是int型数据
printf("%p = %d, ", *(arr + i) + j, *(*(arr + i) + j));
}
}
printf("此处显示了arr,*arr和**arr的值: ");
for (i = 0; i < 4; i++) {
printf("%p = %p -> %d, ", (arr + i), *(arr + i), **(arr + i));
}
printf("直接定义arry[4][3]存储在连续12个int型栈内存空间中: ");
p = arry;
for (i = 0; i < 12; i++) {
printf("%p = %d, ", p + i, *(p + i));
}
printf("动态申请的arr[4][3]存储在堆上,不能直接通过指针连续访问12个int型数据,");
printf("因为malloc申请堆内存实际上是以链表方式来管理的,存在额外的表头空间: ");
p = *arr;
for (i = 0; i < 12; i++) {
printf("%p = %d, ", p + i, *(p + i));
}
printf("释放二维数据的每一行数据的内存空间: ");
for (i = 0; i < 4; i++) {
free(arr[i]);
}
printf("释放行指针的内存空间: ");
free(arr);
printf("结束! ");
return 0;
}
开始:
申请存储行指针的空间:
申请二维数组第0行数据的空间(即arr[0]行的数据):
申请二维数组第1行数据的空间(即arr[1]行的数据):
申请二维数组第2行数据的空间(即arr[2]行的数据):
申请二维数组第3行数据的空间(即arr[3]行的数据):
按照二维数组方式访问动态申请的arr:
直接定义二维数组arry的访问方法:
0x7ffd8ad5b820 = 1, 0x7ffd8ad5b824 = 2, 0x7ffd8ad5b828 = 3,
0x7ffd8ad5b82c = 4, 0x7ffd8ad5b830 = 5, 0x7ffd8ad5b834 = 6,
0x7ffd8ad5b838 = 7, 0x7ffd8ad5b83c = 8, 0x7ffd8ad5b840 = 9,
0x7ffd8ad5b844 = 10, 0x7ffd8ad5b848 = 11, 0x7ffd8ad5b84c = 12,
按照二维数组方式访问动态申请的arr:
0x2406050 = 1, 0x2406054 = 2, 0x2406058 = 3,
0x2406070 = 4, 0x2406074 = 5, 0x2406078 = 6,
0x2406090 = 7, 0x2406094 = 8, 0x2406098 = 9,
0x24060b0 = 10, 0x24060b4 = 11, 0x24060b8 = 12,
arr[i][j]等效访问方式:
0x2406050 = 1, 0x2406054 = 2, 0x2406058 = 3,
0x2406070 = 4, 0x2406074 = 5, 0x2406078 = 6,
0x2406090 = 7, 0x2406094 = 8, 0x2406098 = 9,
0x24060b0 = 10, 0x24060b4 = 11, 0x24060b8 = 12,
此处显示了arr,*arr和**arr的值:
0x2406020 = 0x2406050 -> 1,
0x2406028 = 0x2406070 -> 4,
0x2406030 = 0x2406090 -> 7,
0x2406038 = 0x24060b0 -> 10,
直接定义arry[4][3]存储在连续12个int型栈内存空间中:
0x7ffd8ad5b820 = 1, 0x7ffd8ad5b824 = 2, 0x7ffd8ad5b828 = 3,
0x7ffd8ad5b82c = 4, 0x7ffd8ad5b830 = 5, 0x7ffd8ad5b834 = 6,
0x7ffd8ad5b838 = 7, 0x7ffd8ad5b83c = 8, 0x7ffd8ad5b840 = 9,
0x7ffd8ad5b844 = 10, 0x7ffd8ad5b848 = 11, 0x7ffd8ad5b84c = 12,
动态申请的arr[4][3]存储在堆上,不能直接通过指针连续访问12个int型数据,
因为malloc申请堆内存实际上是以链表方式来管理的,存在额外的表头空间:
0x2406050 = 1, 0x2406054 = 2, 0x2406058 = 3,
0x240605c = 0, 0x2406060 = 0, 0x2406064 = 0,
0x2406068 = 33, 0x240606c = 0, 0x2406070 = 4,
0x2406074 = 5, 0x2406078 = 6, 0x240607c = 0,
释放二维数据的每一行数据的内存空间:
释放行指针的内存空间:
结束!