[说明]
函数DelA - InsB ( LinkedList La, LinkedList Lb, int key 1,int key 2,int len)的功能是,将线性表A中关键码为key 1的节点开始的len个节点,按原顺序移至线性表B中关键码为key 2的节点之前。若移动成功,则返回0;否则返回-1。
线性表的存储结构为带头节点的单链表,La为表A的头指针,Lb为表B的头指针。单链表节点的类型定义如下。
typedef struct node
int key;
struct node*next;
*LinkedList;
[C程序]
int DelA_InsB (LinkedLiSt La, LinkedList Lb, int key1,int key2,int len
LinkedList p, q, S, prep, pres;
int k;
if (!La ->next || !Lb ->next || len<=0)
return-l;
p = La->next;
prep = La;
while (p && p->key != key1)/* 查找表A中键值为key1的节点 */
prep = p;
p = p->next;
if (!p)
return -1; /* 表A中不存在键值为key1的节点 */
q = p;
k = 1;
while (q && (1) ) /* 在表A中找出待删除的len个节点 */
(2) ;
k++;
if (!q)
return -1; /* 表A中不存在要被删除的len个节点 */
S = Lb ->next;
(3) ;
while (s && s->key != key2)/* 查找表B中键值为key2的节点 */
pres = s;
s = e->next;
if (!s)
return -1; /* 表B中不存在键值为key2的节点 */
(4) q->next; /* 将表A中的len个节点删除 */
q->next= (5)
pres->next = p; /* 将len个节点移至表B */
return 0;
参考答案:这是一道要求读者在单链表上实现元素的群插入、群删除操作的程序设计题。本题的解答思路如下。
本程序是在链表插入和删除单个节点的基础上进行扩展的,一次性插入多个节点和删除多个节点。元素的群插入或群删除操作是在只删除一个元素的基础上,通过增加一个寻找指定大小和指定数量节点的过程来实现的。其原理和插入、删除一个节点的运算是一致的。首先在链表A中查找键值为key1的节点。在程序中使用了如下的第1个while循环语句。
while (p && p->key !=key1){ /* 查找表A中键值为key1的节点 */
prep = p;
p = p ->next;
}
若找到键值为key1的节点(即查找成功),则用指针p指示(即p指向该节点),指针prep指向p的直接前驱。然后观察在p的后面是否有len个节点。在程序中使用了如下的第2个while循环。
q = p;k = 1;
while (q && (1) ) { /* 在表A中找出待删除的len个节点 */
(2) ;
k++;}
第2个while循环是为了找到以键值为key1的节点开始的len个节点。若查找成功,指针吁将指向len个节点中的最后一个节点。程序先将q指向p,变量k是用来计算节点个数的计数器。而该循环的结束条件有两个。第1个是p的后面没有len个节点。此时q为空,所以(2)空缺处所填写的语句是“q=q->next”或“q=(*q).next”,使q的指针往后移动。第2个是p的后面有len个节点。此时k=len,所以(1)
空缺处所填写的语句是“k<len”。如果p的后面有len个节点,则q指向第len个节点,如图3-22所示。图 3-22中的虚线表示省略了中间若干个节点。
图3-22 链表示意图1
同理,在链表B中查找键值为key2的节点,使用了如下的第3个while循环语句。
S = Lb->next;
(3) ;
while (s && s->key !=key2) { /* 查找表B中键值为key2的节点 */
pres.=s;s=s->next;
}
以上的程序中,s指向第1个节点,然后进行循环。循环的结束条件有2个:第1个是s为空,即说明从头到尾都没有找到键值为key2的节点;第2个是指针s指向该节点,指针pres指向;的直接前驱,即表示查找成功。但是,当第1个节点的键值就是key2时,根据循环条件,循环中的语句不执行,则pres没有值。所以(3)空缺处所填写的内容是“pres=Lb”,使指针pres始终指向s的前驱,如图3-23所示 (图中的虚线表示省略了中间若干个节点)。
图3-23 链表示意图2
最后将指针p到q的连续len个节点从链表A中删除,在链表B中插入,如图3-24所示。
图3-24 链表示意图3
程序中使用的语句如下。
(4) q->next; /* 将表A中的len个节点删除 */
q->next= (5)
pres->next=p; /* 将len个节点移至表B */
如果要把指针p到q的连续len个节点从链表A中删除,就要把指针p的前驱(prep)的next指向指针q的next,因此(4)空缺处所填写的内容是“prep->next”或“(*prep).next”,
接下来将指针q的next指向线性表B中s,把指针s的前驱(pres)的next指向p,即(5)空缺处所填写的内容是“s”(或“pres->next”,或“(*pres).next”。