// algo2-8.cpp 实现算法2.17的程序 #include"c1.h" #define N 2 typedef char ElemType; #include"c2-3.h" #include"func2-2.cpp" #include"bo2-32.cpp" #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数 void difference(SLinkList space,int &S) // 算法2.17 { // 依次输入集合A和B的元素,在一维数组space中建立表示集合(A-B)∪(B-A) // 的静态链表,S为其头指针。假设备用空间足够大,space[0].cur为备用空间的头指针 int r,p,m,n,i,j,k; ElemType b; InitSpace(space); // 初始化备用空间 S=Malloc(space); // 生成S的头结点 r=S; // r指向S的当前最后结点 printf("请输入集合A和B的元素个数m,n:"); scanf("%d,%d%*c",&m,&n); // %*c吃掉回车符 printf("请输入集合A的元素(共%d个):",m); for(j=1;j<=m;j++) // 建立集合A的链表 { i=Malloc(space); // 分配结点 scanf("%c",&space[i].data); // 输入A的元素值 space[r].cur=i; // 插入到表尾 r=i; } scanf("%*c"); // %*c吃掉回车符 space[r].cur=0; // 尾结点的指针为空 printf("请输入集合B的元素(共%d个):",n); for(j=1;j<=n;j++) { // 依次输入B的元素,若不在当前表中,则插入;否则删除 scanf("%c",&b); p=S; k=space[S].cur; // k指向集合A中的第一个结点 while(k!=space[r].cur&&space[k].data!=b) { // 在当前表中查找 p=k; k=space[k].cur; } if(k==space[r].cur) { // 当前表中不存在该元素,插入在r所指结点之后,且r的位置不变 i=Malloc(space); space[i].data=b; space[i].cur=space[r].cur; space[r].cur=i; } else // 该元素已在表中,删除之 { space[p].cur=space[k].cur; Free(space,k); if(r==k) r=p; // 若删除的是尾元素,则需修改尾指针 } } } void main() { int k; SLinkList s; difference(s,k); ListTraverse(s,k,print2); }
运行结果如下:
// algo2-9.cpp 尽量采用bo2-31.cpp中的基本操作实现算法2.17的功能 #include"c1.h" #define N 2 typedef char ElemType; #include"c2-3.h" #include"func2-2.cpp" #include"bo2-31.cpp" #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数 void difference(SLinkList space) // 改进算法2.17(尽量利用基本操作实现) { // 依次输入集合A和B的元素,在一维数组space中建立表示集合(A-B)∪(B-A)的静态链表 int m,n,i,j; ElemType b,c; InitList(space); // 构造空链表 printf("请输入集合A和B的元素个数m,n:"); scanf("%d,%d%*c",&m,&n); // %*c吃掉回车符 printf("请输入集合A的元素(共%d个):",m); for(j=1;j<=m;j++) // 建立集合A的链表 { scanf("%c",&b); // 输入A的元素值 ListInsert(space,1,b); // 插入到表头 } scanf("%*c"); // 吃掉回车符 printf("请输入集合B的元素(共%d个):",n); for(j=1;j<=n;j++) { // 依次输入B的元素,若不在当前表中,则插入;否则删除 scanf("%c",&b); for(i=1;i<=ListLength(space);i++) { GetElem(space,i,c); // 依次求得表中第i个元素的值,并将其赋给c if(c==b) // 表中存在b,且其是第i个元素 { ListDelete(space,i,c); // 删除第i个元素 break; // 跳出i循环 } } if(i>ListLength(space)) // 表中不存在b ListInsert(space,1,b); // 将b插在表头 } } void main() { SLinkList s; difference(s); ListTraverse(s,print2); }
运行结果如下:
/* algo2-9.cpp 是用静态链表的基本操作来实现算法2.17 功能的。由于只用到1 个链 表,故采用bo2-31.cpp 中的基本操作;又由于集合是与顺序无关的,而链表的插入以插 在表头效率最高,故在algo2-9.cpp 中插入元素时均插在表头。这只影响集合中元素的输 出顺序。将algo2-9.cpp 与algo2-8.cpp 对比可见,采用基本操作可使程序简洁明了,思路 清晰,因此在编程时应尽量采用已有的基本操作,以提高效率 */