兩種頭插法分別建立一個鏈表,然後合并,按非遞減型輸出:
#include<iostream> /* 函數結果狀態碼 */ #define TRUE 1 #define FALSE 0 #define OK 1 #define ERROR 0 #define INFEASIBLE -1 #define OVERFLOW -2 using namespace std; typedef int Status; /* Status是函數的類型,其值是函數結果狀態碼,如OK等 */ typedef int ElemType; struct LNode { ElemType data; LNode *next; }; typedef LNode *LinkList; Status InitList(LinkList *L) { /* 操作結果:構造一個空的線性表L */ *L=(LinkList)malloc(sizeof(struct LNode)); /* 產生頭結點,並使L指向此頭結點 */ if(!*L) /* 儲存分配失敗 */ exit(OVERFLOW); (*L)->next=NULL; /* 指標域為空白 */ return OK; } Status GetElem(LinkList L,int i,ElemType *e) /* 演算法2.8 */ { /* L為帶頭結點的單鏈表的頭指標。當第i個元素存在時,其值賦給e並返回OK,否則返回ERROR */ int j=1; /* j為計數器 */ LinkList p=L->next; /* p指向第一個結點 */ while(p&&j<i) /* 順指標向後尋找,直到p指向第i個元素或p為空白 */ { p=p->next; j++; } if(!p||j>i) /* 第i個元素不存在 */ return ERROR; *e=p->data; /* 取第i個元素 */ return OK; } Status ListInsert(LinkList L,int i,ElemType e) /* 演算法2.9。不改變L */ { /* 在帶頭結點的單鏈線性表L中第i個位置之前插入元素e */ int j=0; LinkList p=L,s; while(p&&j<i-1) /* 尋找第i-1個結點 */ { p=p->next; j++; } if(!p||j>i-1) /* i小於1或者大於表長 */ return ERROR; s=(LinkList)malloc(sizeof(struct LNode)); /* 產生新結點 */ s->data=e; /* 插入L中 */ s->next=p->next; p->next=s; return OK; } Status ListTraverse(LinkList L,void(*vi)(ElemType)) /* vi的形參類型為ElemType,與bo2-1.c中相應函數的形參類型ElemType&不同 */ { /* 初始條件:線性表L已存在 */ /* 操作結果:依次對L的每個資料元素調用函數vi()。一旦vi()失敗,則操作失敗 */ LinkList p=L->next; while(p) { vi(p->data); p=p->next; } cout<<endl; return OK; } void CreateList(LinkList &L,int n) // { // 逆位序(插在表頭)輸入n個元素的值,建立帶表頭結構的單鏈線性表L int i; LinkList p; L=(LinkList)malloc(sizeof(LNode)); L->next=NULL; // 先建立一個帶頭結點的單鏈表 cout<<"請輸入"<<n<<"個資料\n"; for(i=n;i>0;--i) { p=(LinkList)malloc(sizeof(LNode)); // 產生新結點 scanf("%d",&p->data); // 輸入元素值 p->next=L->next; // 插入到表頭 L->next=p; //這就是書上的那個頭插法~~ } } void CreateList2(LinkList &L,int n) { // 正位序(插在表尾)輸入n個元素的值,建立帶表頭結構的單鏈線性表 int i; LinkList p,q; L=(LinkList)malloc(sizeof(LNode)); // 產生頭結點 L->next=NULL; q=L; cout<<"請輸入"<<n<<"個資料\n"; for(i=1;i<=n;i++) { p=(LinkList)malloc(sizeof(LNode)); cin>>p->data; q->next=p; q=q->next; //這就是另一種頭插法~~ } p->next=NULL; } void MergeList(LinkList La,LinkList &Lb,LinkList &Lc)// { // 已知單鏈線性表La和Lb的元素按值非遞減排列。 // 歸併La和Lb得到新的單鏈線性表Lc,Lc的元素也按值非遞減排列 LinkList pa=La->next,pb=Lb->next,pc; Lc=pc=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; // 插入剩餘段 free(Lb); // 釋放Lb的頭結點 Lb=NULL; } void visit(ElemType c) // ListTraverse()調用的函數(類型要一致) { cout<<c<<" "; }int main() { int n=5; LinkList La,Lb,Lc; cout<<"按非遞減順序, "; CreateList2(La,n); // 正位序輸入n個元素的值 cout<<"La="; // 輸出鏈表La的內容 ListTraverse(La,visit); cout<<"按非遞增順序, "; CreateList(Lb,n); // 逆位序輸入n個元素的值 cout<<"Lb="; // 輸出鏈表Lb的內容 ListTraverse(Lb,visit); MergeList(La,Lb,Lc); // 按非遞減順序歸併La和Lb,得到新表Lc cout<<"合并後按非遞減型輸出\nLc="; // 輸出鏈表Lc的內容 ListTraverse(Lc,visit); }