目录
2.7 线性表的应用
2.7.1 线性表的合并
算法思想:依次取出Lb中的每个元素,执行以下操作:
1. 在La中查找该元素;
2. 如果找不到,则将其插入La的最后。
void union(List &La, List Lb){
La_len = ListLength(La);
Lb_len = ListLength(Lb);
for(i=1; i<=Lb_len; i++)
{
GetElem(Lb, i, e);
if(!LocateElem(La, e))
ListInsert(&La, ++La_len, e);
}
}
Lb的长度每次都要在La中寻找,所以算法时间复杂度为O(ListLength(La)*ListLength(Lb))
2.7.2 有序表的合并
算法思想:
1. 创建一个空表Lc;
2. 依次从 La 或 Lb 中“摘取”元素值较小的结点插入到 Lc 表的最后,直至其中一个表变空为止;
3. 继续将 La 或 Lb 其中一个表的剩余结点插入在 Lc 表的最后。
(1)用顺序表实现
void MergeList_Sq(SqList LA, SqList LB, SqList &LC){
pa = LA.elem;
pb = LB.elem; // 指针pa和pb的初值分别指向两个表的第一个元素
LC.length = LA.length + LB.length; // 新表长度为待合并量表的长度之和
LC.elem = new ElemType[LC.length]; // 为合并后的新表分配一个数组空间
pc = LC.elem; // 指针pc指向新表的第一个元素
pa_last = LA.elem + LA.length - 1; // 指针pa_last指向LA表的最后一个元素,基地址+长度-1
pb_last = LB.elem + LB.length - 1; // 指针pb_last指向LB表的最后一个元素
while(pa<=pa_last && pb<=pb_las) // 两个表都非空
{
if(*pa <= *pb)
*pc++ = *pa++; // 依次“摘取”两表中值较小的结点
else
*pc++ = *pb++;
}
while(pa <= pa_last)
*pc++ = *pa++; // LB表已到达表尾,将LA中剩余元素加入LC
while(pb <= pb_last)
*pc++ = *pb++; // LA表已到达表尾,将LB中剩余元素加入LC
} // MergeList_Sq
算法时间复杂度=0(ListLength(La) + ListLength(Lb)) // La, Lb长度之和
算法空间复杂度=0(ListLength(La) + ListLength(Lb)) // La, Lb元素之和
(2)用链表实现
算法实现:
void MergeList_L(LinkList &La, LinkList &Lb, LinkList &Lc){
pa = La -> next;
pb = Lb -> next;
pc = Lc = La; // 用La的头结点作为Lc的头结点
while(pa && pb)
{
if(pa -> data <= pb -> data)
{
pc -> next = pa;
pc = pa;
pa = pa -> next;
}
else
{
pc -> next = pb;
pc = pb;
pb = pb -> next;
}
}
pc -> next = pa?pa:pb; // 插入剩余段
delete Lb; // 释放Lb的头结点
}
算法时间复杂度=0(ListLength(La) + ListLength(Lb)) // La, Lb的结点都要访问一遍
算法空间复杂度=0(1) // 不需要额外空间,删了Lb头结点多了Lc的
2.8 案例分析与实现
2.8.1 一元多项式的运算:实现两个多项式加、减、乘运算
2.8.2 稀疏多项式的运算
建立链表:
void CreatePolyn(Polynomial &P, int n){ // 输入m项的系数和指数,建立表示多项式的有序链表P
P = new PNode;
P -> next = NULL; // 先输入一个带头结点的单链表
for(i=1; i<n; ++i) // 依次输入n个非零项
{
s = new PNode; // 生成新结点
cin >> s -> coef >> s-> expn; // 输入系数和指数
pre = P; // pre用于保存q的前驱,初值为头结点
q = P -> next; // q初始化,指向首元结点
while(q && q->expn < s->expn) // 找到第一个大于输入项指数的项*q
{
pre = q;
q = q -> next;
}
s -> next = q; // 将输入项s插入到q和其前驱结点pre之间
pre -> next = s;
}
}
比较求和:
2.8.3 图书信息管理系统