动态分配
动态分配一位数组,存储数组的空间在程序执行过程中通过动态存储分配语句分配的,一旦数据空间占满,就另外开辟一块更大的存储空间,用以替换原来的存储空间,从而达到扩充存储数组空间的目的,而不需要为线性表一次性地划分所有空间。
大致上都与静态分配一致,只有以下几点不同
1)结构体中换为指示冬天分配数组的指针
2)数组的最大容量可以扩充
3)初始化要用malloc
4) 扩充时要新写一个扩充函数IncreaseList
扩充函数即重新分配一块空间,将原来的内容复制过来,然后释放原来的空间。
5) DestroyList不同,静态分配由内存自动回收,而动态分配要手动free
#include<stdio.h>
#include<stdlib.h>//malloc free函数的头文件
#define InitSize 20//默认的最大长度
//线性表顺序表示 一维数组的动态分配
//动态分配时,存储数组的空间是在程序执行过程中通过动态存储分配语句分配的,一旦
//数据空间占满,就另外开辟一块更大的存储空间,用以代替原来的存储空间,从而
//达到扩充存储数组空间的目的
typedef struct{
int *data; //指示动态分配数组的指针
int MaxSize,len;//数组的最大容量和当前个数
}SqList;
void InitList(SqList &L){
//L.data=NULL;
L.data=(int*)malloc(InitSize*sizeof(int));
L.MaxSize=InitSize;
L.len=0;
}
int Length(SqList L){
return L.len;
}
//按值查找
int LocateElem(SqList L,int e){
for(int i=0; i<L.len;i++){
if(L.data[i] == e)
return i+1;//返回此元素在顺序表中的位置(从1开始)
}
return 0;//未找到
}
//按位查找
int GetElem(SqList L,int i){
if(i<1||i>L.len){
printf("非法位序!\n");
return 0;//位置非法
}
return L.data[i-1];
}
//增加动态分配数组的长度,加长len的长度
void IncreaseSize(SqList &L, int len){
int *p=L.data;
L.data=(int*)malloc((L.len+len)*sizeof(int));
for(int i=0;i<=L.len;i++){//@@@ <=
L.data[i]=p[i];
}
for(int i=L.len;i<L.len+len;i++){//新增加的初始化为0
L.data[i]=0;
}
L.MaxSize=L.MaxSize+len;//@@@
free(p);//@@@@内存被释放掉了,但是p的指向没变
p=NULL;//将地址置0,防止产生野指针
}
//在L的第i个位置上插入e @@@判断是否超出MaxSize
bool InsertList(SqList &L,int i,int e){
if(i < 1 || i > L.len+1)//插入位置不合法
return false;
if(L.len > L.MaxSize){//@@@这里不能是InitSize
/* printf("超出数组最大长度空间\n");
return false;
*/
IncreaseSize(L,20);
//printf("L.len=%d, L.data[21]=%d\n",L.len,L.data[20]);
}
for(int j = L.len; j >= i; j--){//把i后面的都往后移动一个位置
L.data[j]=L.data[j-1];
}
L.data[i-1]=e;//@@@
L.len++;//@@@
return true;//插入成功
}
//删除操作,删除L中第i个位置的元素,用e返回删除元素的值
bool DeleteList(SqList &L,int i,int &e){
if(i<1||i>L.len)
return false;//删除位置不合法
e=L.data[i-1];//@@@
for(int j=i-1;j<L.len;j++){//@@@
L.data[j]=L.data[j+1];
}
L.len--;
return true;
}
void PrintList(SqList L){
printf("(length:%d)List is: ",L.len);
for(int i = 0; i < L.len; i++){
if(i%20==0){
printf("\n");
}
printf("%3d ",L.data[i]);
}
printf("\n");
}
bool Empty(SqList L){
return L.len==0;
}
void DestroyList(SqList &L){
L.len=0;
int *p=L.data;
free(p);
p=NULL;
}
int main(){
SqList L;//声明一个顺序表
InitList(L);
for(int i=0; i<43; i++){
InsertList(L,i+1,i+1);
}
printf("插入后的链表为:\n");
PrintList(L);
/*
int e;
printf("\n");
if(DeleteList(L,6,e)){
printf("%d ",e);
}
printf("\n");
InsertList(L,10,e);
PrintList(L);
int i=GetElem(L,11);
if(i){
printf("数值是:%d\n",i);
}
DestroyList(L);
PrintList(L);
*/
return 0;
}
运行结果: