q=L.elem+L.length-1顺序存储结构(实际上就是数组)中,l.elem表示线性表l中存储数据(数组)的基地址(起始地址)这个也就是一开始建立顺序表的原因,其实本质上就是进行了用程序模拟了c语言中的数组,之所一开始 int* elem 的原因就是 和 数组中的的定义一样,例如数组a[2] a就是 a[0]的地址,即 a == &a[0],l.length是表的长度(数据元素个数),q是指针通过上式计算后指向尾元素和数组的情况一样,例如:int a[10],*p=a;//p指向第一个元素
p=a+1;//指向第二个元素.
例如:p=a+10-1;指向最后一个数组元素,即a[9].
for(++p;p<=q;++p)p是一个被初始化过的指针,按上面代码应该指向某类型的数组,为超表达方便,数组记为x(i)。for循环首先把p从当前位置x(k)移动到x(k+1)作为初值,只要指针没到q指向的位置,就继续循环,循环每次递增一个数据。循环体将数组当前位置数据拷贝到前一个位置。总之,初始时,如果p指向x(m),q指向x(n),n应该大于m。最终运行结果是x(m)=x(m+1)=...=x(n)。
删除操作中函数的返回值是int型的,当然也可以是void的型的,如果是void型的话,把return 0;写成return;就好了。
顺序表合并有两个顺序表LA 和 LB,其元素均为非递减有序排列,可设两个指针i、j 分别指向表LA 和 LB 中的元素,若LA.elem[i]>LB.elem[j],则当前先将LB.elem[j]插入到表LC中,若LA.elem[i]<=LB.elem[j],则当前先将LA.elem[i]插入到表LC中,如此进行下去,其中一个表被扫描完毕,然后再将未扫描完的表中剩余的所有元素放到表LC中。其中个一个表被扫描完毕,然后再将未扫描完的表中剩余的所有元素放到表LC中。
算法演示 #include<stdio.h> #include<stdlib.h> #define MAX 20 typedef struct{ int *elem; int length; int listsize; }SqList; void CreatList(SqList &L) {//建立一个线性表 L.elem=(int*)malloc(MAX *sizeof(int)); if(!L.elem) return;//exit(0) L.listsize=MAX; printf("输入La表的长度:"); scanf("%d",&L.length); printf("输入%d个数:",L.length); for(int i=0;i<L.length;i++) scanf("%d",&L.elem[i]); } //创建第二个表 void CreatList2(SqList &L2) { L2.elem=(int*)malloc(MAX *sizeof(int)); if(!L2.elem) return;//exit(0) L2.listsize=MAX; printf("输入Lb表的长度:"); scanf("%d",&L2.length); printf("输入%d个数:",L2.length); for(int i=0;i<L2.length;i++) scanf("%d",&L2.elem[i]); } void Traverse(SqList L){ //遍历 printf("La中数据为:"); for(int i=0;i<L.length;i++) printf("%3d",L.elem[i]); printf("\n"); } void Traverse2(SqList L2){ //遍历 printf("Lb表中数据为:"); for(int i=0;i<L2.length;i++) printf("%3d",L2.elem[i]); printf("\n"); } void Traverse3(SqList L3){ //遍历 printf("组合表Lc中数据为:"); for(int i=0;i<L3.length;i++) printf("%3d",L3.elem[i]); printf("\n"); } void MergeList_Sq(SqList la,SqList lb,SqList &lc)//增加的是lc的操作,前面的几个例子也说名了,只要牵扯到改变表中数据 //就用引用符号& { int* pa = la.elem; // 对顺序表中第一个元素的地址进行初始化 int* pb = lb.elem; lc.listsize = lc.length = la.length + lb.length; //Lc表初始化大小 int* pc = lc.elem = (int*)malloc(MAX *sizeof(int)); //请求系统进行动态内存分配 if (!lc.elem) { return;//存储分配失败 } int* pa_last = la.elem + la.length - 1; //定义La 顺序表中末尾元素的地址,而且在线性表中地址都是递增,且递增幅度不变 int* pb_last = lb.elem + lb.length - 1; //看下面的图就清晰了 while (pa <= pa_last && pb <= pb_last) //其实都是比较的地址 ,还有就是注意<= 不要写成< { if (*pa <= *pb)//对于指针指向的内容作比较 { *pc++ = *pa++; // 等价于 *pc = *pa; *pa++; *pc++;注意此处的 *pa++ 不可以写成* (++pa),说明看算法小结 } else { *pc++ = *pb++; } } while (pa <= pa_last) *pc++ = *pa++;//插入La的剩余元素 while (pb <= pb_last) *pc++ = *pb++; } int main(){ SqList L,L2,L3; CreatList(L); Traverse(L); CreatList2(L2); Traverse2(L2); MergeList_Sq(L,L2,L3); Traverse3(L3); return 0; } 运行演示 算法小结int* pa_last = la.elem + la.length - 1; 这段代码就是求表中最后一个元素的地址,而地址是按一定的幅度递增的,如下图