构造动态数组

程序员成长之旅 · 程序员成长之旅/C语言/笔记 · 1236 字

构建所需函数

函数原型 返 回 功能说明
void *malloc(unsigned int size); 成功:返回所开辟 空间首地址 失败:返回空指针 向系统申请 size字节的 堆空间
void *calloc(unsigned int num, unsigned int size); 成功:返回所开辟 空间首地址 失败:返回空指针 按类型申请 num个size字 节的堆空间
void free(void *p); 无返回值 释放p指向 的堆空间
void *realloc(void *p,unsigned int size); 成功:返回新开辟 空间首地址 失败:返回空指针 将p指向的 堆空间变为 size来源: https://www.runoob.com/w3cnote/c-dynamic-array.html

说明:

(3)由于动态分配不一定成功,为此要附加一段异常处理程序,不致程序运行停止,使用户 不知所措。通常采用这样的异常处理程序段: if(p==NULL) /* 或者if(!p)*/ { printf("动态申请内存失败!\n"); exit(1); //异 常退出 }

malloc与calloc的区别

对于用malloc分配的内存区间,如果原来没有被使用过,则其中的每一位可能都是0;反之, 如果这部分内存空间曾经被分配、释放和重新分配,则其中可能遗留各种各样的数据。也就是说, 使用malloc()函数的程序开始时(内存空间还没有被重新分配)能正常运行,但经过一段时间后(内 存空间已被重新分配)可能会出现问题,因此在使用它之前必须先进行初始化(可用memset函数 对其初始化为0),但调用calloc()函数分配到的空间在分配时就已经被初始化为0了。 当你在calloc()函数和malloc()函数之间作选择时,你需考虑是否要初始化所分配的内存空 间,从而来选择相应的函数。

具体构建方法

以三维整型数组array[n1][n2][n3]为例。

先遵循从外层到里层,逐层申请的原则:

最外层指针是array,它是个三维指针,所指向的是array[],其为二维指针。所以给array

申请内存应:

//以三维整型数组array[n1][n2][n3]为例。
array=(int***)calloc(n1,sizeof(int**));

//次层指针是array[],它是个二维指针,所指向的是array[][],其为一维指针。所以给array[] 申请内存应:
for(i=0;i<n1;i++)
{
    array[i]=(int**)calloc(n2,sizeof(int*));
}

//最内层指针是array[][],它是个一维指针,所指向的是array[][][],其是个整型常量。所以给array[][]申请内存应:
for(i=0;i<n1;i++)
{
    for(j=0;j<n2;j++)
    {
        array[i][j]=(int*)calloc(n3,sizeof(int));
    }
}

//当然,你可以把它们整合在一起为:

int i,j,k;
int n1,n2,n3;
int ***array;
scanf("%d%d%d",&n1,&n2,&n3);
array=(int***)calloc(n1,sizeof(int**));
for(i=0;i<n1;i++)
{
    array[i]=(int**)calloc(n2,sizeof(int*));
    for(j=0;j<n2;j++)
    {
        array[i][j]=(int*)calloc(n3,sizeof(int));
        for(k=0;k<n3;k++)
        {
            array[i][j][k]=i+j+k+1;
        }
    }
}



//最后不要忘了释放这些内存,这要遵循释放的时候从里层往外层,逐层释放的原则。分析过程可参考上面的解答,这里不再赘述。只给出代码吧:
for(i=0;i<n1;i++)
{
    for(j=0;j<n2;j++)
    {
        free(array[i][j]);//释放第三维指针
    }
}
for(i=0;i<n1;i++)
{
    free(array[i]);//释放第二维指针
}
free(array);//释放第一维指针