algo2-01~2-13.cpp 线性表-主程序的实现

                  1.  // algo2-9.cpp 尽量采用bo2-31.cpp中的基本操作实现算法2.17的功能
                  2.  #include"c1.h"
                  3.  #define N 2
                  4.  typedef char ElemType;
                  5.  #include"c2-3.h"
                  6.  #include"func2-2.cpp"
                  7.  #include"bo2-31.cpp"
                  8.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                  9.  void difference(SLinkList space) // 改进算法2.17(尽量利用基本操作实现)
                  10.  { // 依次输入集合A和B的元素,在一维数组space中建立表示集合(A-B)∪(B-A)的静态链表
                  11.    int m,n,i,j;
                  12.    ElemType b,c;
                  13.    InitList(space); // 构造空链表
                  14.    printf("请输入集合A和B的元素个数m,n:");
                  15.    scanf("%d,%d%*c",&m,&n); // %*c吃掉回车符
                  16.    printf("请输入集合A的元素(共%d个):",m);
                  17.    for(j=1;j<=m;j++) // 建立集合A的链表
                  18.    {
                  19.      scanf("%c",&b); // 输入A的元素值
                  20.      ListInsert(space,1,b); // 插入到表头
                  21.    }
                  22.    scanf("%*c"); // 吃掉回车符
                  23.    printf("请输入集合B的元素(共%d个):",n);
                  24.    for(j=1;j<=n;j++)
                  25.    { // 依次输入B的元素,若不在当前表中,则插入,否则删除
                  26.      scanf("%c",&b);
                  27.      for(i=1;i<=ListLength(space);i++)
                  28.      {
                  29.        GetElem(space,i,c); // 依次求得表中第i个元素的值,并将其赋给c
                  30.        if(c==b) // 表中存在b,且其是第i个元素
                  31.        {
                  32.      ListDelete(space,i,c); // 删除第i个元素
                  33.          break// 跳出i循环
                  34.        }
                  35.      }
                  36.      if(i>ListLength(space)) // 表中不存在b
                  37.        ListInsert(space,1,b); // 将b插在表头
                  38.    }
                  39.  }
                  40.  void main()
                  41.  {
                  42.    SLinkList s;
                  43.    difference(s);
                  44.    ListTraverse(s,print2);
                  45.  }
                  1.  // algo2-10.cpp 两个仅设表尾指针的循环链表的合并(教科书图2.13)
                  2.  #include"c1.h"
                  3.  typedef int ElemType;
                  4.  #include"c2-2.h"
                  5.  #include"bo2-4.cpp"
                  6.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                  7.  void MergeList(LinkList &La,LinkList Lb)
                  8.  { // 将Lb合并到La的表尾,由La指示新表
                  9.    LinkList p=Lb->next;
                  10.    Lb->next=La->next;
                  11.    La->next=p->next;
                  12.    free(p);
                  13.    La=Lb;
                  14.  }
                  15.  void main()
                  16.  {
                  17.    int n=5,i;
                  18.    LinkList La,Lb;
                  19.    InitList(La);
                  20.    for(i=1;i<=n;i++)
                  21.      ListInsert(La,i,i);
                  22.    printf("La="); // 输出链表La的内容
                  23.    ListTraverse(La,print);
                  24.    InitList(Lb);
                  25.    for(i=1;i<=n;i++)
                  26.      ListInsert(Lb,1,i*2);
                  27.    printf("Lb="); // 输出链表Lb的内容
                  28.    ListTraverse(Lb,print);
                  29.    MergeList(La,Lb);
                  30.    printf("La+Lb="); // 输出合并后的链表的内容
                  31.    ListTraverse(La,print);
                  32.  }
                  1.  // algo2-11.cpp 实现算法2.20、2.21的程序
                  2.  #include"c1.h"
                  3.  typedef int ElemType;
                  4.  #include"c2-5.h"
                  5.  #include"bo2-6.cpp"
                  6.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                  7.  Status ListInsert_L(LinkList &L,int i,ElemType e) // 算法2.20
                  8.  { // 在带头结点的单链线性表L的第i个元素之前插入元素e
                  9.    Link h,s;
                  10.    if(!LocatePos(L,i-1,h))
                  11.      return ERROR; // i值不合法
                  12.    MakeNode(s,e); // 结点分配失败则退出
                  13.    InsFirst(L,h,s); // 对于从第i个结点开始的链表,第i-1个结点是它的头结点
                  14.    return OK;
                  15.  }
                  16.  void MergeList_L(LinkList &La,LinkList &Lb,LinkList &Lc,int(*compare)(ElemType,ElemType))
                  17.  { // 已知单链线性表La和Lb的元素按值非递减排列。归并La和Lb得到新的单链
                  18.    // 线性表Lc,Lc的元素也按值非递减排列。算法2.21
                  19.    Link ha,hb,pa,pb,q;
                  20.    ElemType a,b;
                  21.    InitList(Lc); // 存储空间分配失败则退出
                  22.    ha=GetHead(La); // ha和hb分别指向La和Lb的头结点
                  23.    hb=GetHead(Lb);
                  24.    pa=NextPos(ha); // pa和pb分别指向La和Lb的首元结点
                  25.    pb=NextPos(hb);
                  26.    while(pa&&pb) // La和Lb均非空
                  27.    {
                  28.      a=GetCurElem(pa); // a和b为两表中当前比较元素(第1个元素)
                  29.      b=GetCurElem(pb);
                  30.      if(compare(a,b)<=0) // a<=b
                  31.      {
                  32.        DelFirst(La,ha,q); // 移去La的首元结点并以q返回
                  33.        q->next=NULL; // 将q的next域赋值NULL,以便调用Append()
                  34.        Append(Lc,q); // 将q结点接在Lc的尾部
                  35.        pa=NextPos(ha); // pa指向La新的首元结点
                  36.      }
                  37.      else // a>b
                  38.      {
                  39.        DelFirst(Lb,hb,q); // 移去Lb的首元结点并以q返回
                  40.        q->next=NULL; // 将q的next域赋值NULL,以便调用Append()
                  41.        Append(Lc,q); // 将q结点接在Lc的尾部
                  42.        pb=NextPos(hb); // pb指向Lb新的首元结点
                  43.      }
                  44.    }
                  45.    if(pa) // La非空
                  46.      Append(Lc,pa); // 链接La中剩余结点
                  47.    else // Lb非空
                  48.      Append(Lc,pb); // 链接Lb中剩余结点
                  49.    free(ha); // 销毁La和Lb
                  50.    La.head=La.tail=NULL;
                  51.    La.len=0;
                  52.    free(hb);
                  53.    Lb.head=Lb.tail=NULL;
                  54.    Lb.len=0;
                  55.  }
                  56.  int diff(ElemType c1,ElemType c2)
                  57.  {
                  58.    return c1-c2;
                  59.  }
                  60.  void main()
                  61.  {
                  62.    LinkList La,Lb,Lc;
                  63.    int j;
                  64.    InitList(La);
                  65.    for(j=1;j<=5;j++)
                  66.      ListInsert_L(La,j,j); // 顺序插入 1、2、3、4、5
                  67.    printf("La=");
                  68.    ListTraverse(La,print);
                  69.    InitList(Lb);
                  70.    for(j=1;j<=5;j++)
                  71.      ListInsert_L(Lb,j,2*j); // 顺序插入 2、4、6、8、10
                  72.    printf("Lb=");
                  73.    ListTraverse(Lb,print);
                  74.    MergeList_L(La,Lb,Lc,diff); // 归并La和Lb,产生Lc
                  75.    printf("Lc=");
                  76.    ListTraverse(Lc,print);
                  77.    DestroyList(Lc);
                  78.  }
                  1.  // algo2-12.cpp 用单链表实现算法2.1,仅有4句与algo2-1.cpp不同
                  2.  #include"c1.h"
                  3.  typedef int ElemType;
                  4.  #include"c2-2.h" // 此句与algo2-1.cpp不同(因为采用不同的结构)
                  5.  #include"bo2-2.cpp" // 此句与algo2-1.cpp不同(因为采用不同的结构)
                  6.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                  7.  void Union(LinkList La,LinkList Lb) // 算法2.1,此句与algo2-1.cpp不同
                  8.  { // 将所有在线性表Lb中但不在La中的数据元素插入到La中
                  9.    ElemType e;
                  10.    int La_len,Lb_len;
                  11.    int i;
                  12.    La_len=ListLength(La); // 求线性表的长度
                  13.    Lb_len=ListLength(Lb);
                  14.    for(i=1;i<=Lb_len;i++)
                  15.    {
                  16.      GetElem(Lb,i,e); // 取Lb中第i个数据元素赋给e
                  17.      if(!LocateElem(La,e,equal)) // La中不存在和e相同的元素,则插入之
                  18.        ListInsert(La,++La_len,e);
                  19.    }
                  20.  }
                  21.  void main()
                  22.  {
                  23.    LinkList La,Lb; // 此句与algo2-1.cpp不同(因为采用不同的结构)
                  24.    int j;
                  25.    InitList(La); // 创建空表La。如不成功,则会退出程序的运行
                  26.    for(j=1;j<=5;j++) // 在表La中插入5个元素
                  27.      ListInsert(La,j,j);
                  28.    printf("La= "); // 输出表La的内容
                  29.    ListTraverse(La,print);
                  30.    InitList(Lb); // 创建空表Lb
                  31.    for(j=1;j<=5;j++) // 在表Lb中插入5个元素
                  32.      ListInsert(Lb,j,2*j);
                  33.    printf("Lb= "); // 输出表Lb的内容
                  34.    ListTraverse(Lb,print);
                  35.    Union(La,Lb);
                  36.    printf("new La= "); // 输出新表La的内容
                  37.    ListTraverse(La,print);
                  38.  }
                  1.  // algo2-13.cpp 采用单链表结构实现算法2.2的程序,仅有4句与algo2-2.cpp不同
                  2.  #include"c1.h"
                  3.  typedef int ElemType;
                  4.  #include"c2-2.h" // 此句与algo2-2.cpp不同
                  5.  #include"bo2-2.cpp" // 此句与algo2-2.cpp不同
                  6.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                  7.  void MergeList(LinkList La,LinkList Lb,LinkList &Lc) // 算法2.2,此句与algo2-2.cpp不同
                  8.  { // 已知线性表La和Lb中的数据元素按值非递减排列。
                  9.    // 归并La和Lb得到新的线性表Lc,Lc的数据元素也按值非递减排列
                  10.    int i=1,j=1,k=0;
                  11.    int La_len,Lb_len;
                  12.    ElemType ai,bj;
                  13.    InitList(Lc); // 创建空表Lc
                  14.    La_len=ListLength(La);
                  15.    Lb_len=ListLength(Lb);
                  16.    while(i<=La_len&&j<=Lb_len) // 表La和表Lb均非空
                  17.    {
                  18.      GetElem(La,i,ai);
                  19.      GetElem(Lb,j,bj);
                  20.      if(ai<=bj)
                  21.      {
                  22.        ListInsert(Lc,++k,ai);
                  23.        ++i;
                  24.      }
                  25.      else
                  26.      {
                  27.        ListInsert(Lc,++k,bj);
                  28.        ++j;
                  29.      }
                  30.    }
                  31.    while(i<=La_len) // 表La非空且表Lb空
                  32.    {
                  33.      GetElem(La,i++,ai);
                  34.      ListInsert(Lc,++k,ai);
                  35.    }
                  36.    while(j<=Lb_len) // 表Lb非空且表La空
                  37.    {
                  38.      GetElem(Lb,j++,bj);
                  39.      ListInsert(Lc,++k,bj);
                  40.    }
                  41.  }
                  42.  void main()
                  43.  {
                  44.    LinkList La,Lb,Lc; // 此句与algo2-2.cpp不同
                  45.    int j,a[4]={3,5,8,11},b[7]={2,6,8,9,11,15,20}; // 教科书例2–2的数据
                  46.    InitList(La); // 创建空表La
                  47.    for(j=1;j<=4;j++) // 在表La中插入4个元素
                  48.      ListInsert(La,j,a[j-1]);
                  49.    printf("La= "); // 输出表La的内容
                  50.    ListTraverse(La,print);
                  51.    InitList(Lb); // 创建空表Lb
                  52.    for(j=1;j<=7;j++) // 在表Lb中插入7个元素
                  53.      ListInsert(Lb,j,b[j-1]);
                  54.    printf("Lb= "); // 输出表Lb的内容
                  55.    ListTraverse(Lb,print);
                  56.    MergeList(La,Lb,Lc);
                  57.    printf("Lc= "); // 输出表Lc的内容
                  58.    ListTraverse(Lc,print);
                  59.  }
                   // algo2-8.cpp 实现算法2.17的程序
                1.  #include"c1.h"
                2.  #define N 2
                3.  typedef char ElemType;
                4.  #include"c2-3.h"
                5.  #include"func2-2.cpp"
                6.  #include"bo2-32.cpp"
                7.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
                8.  void difference(SLinkList space,int &S) // 算法2.17
                9.  { // 依次输入集合A和B的元素,在一维数组space中建立表示集合(A-B)∪(B-A)
                10.    // 的静态链表,S为其头指针。假设备用空间足够大,space[0].cur为备用空间的头指针
                11.    int r,p,m,n,i,j,k;
                12.    ElemType b;
                13.    InitSpace(space); // 初始化备用空间
                14.    S=Malloc(space); // 生成S的头结点
                15.    r=S; // r指向S的当前最后结点
                16.    printf("请输入集合A和B的元素个数m,n:");
                17.    scanf("%d,%d%*c",&m,&n); // %*c吃掉回车符
                18.    printf("请输入集合A的元素(共%d个):",m);
                19.    for(j=1;j<=m;j++) // 建立集合A的链表
                20.    {
                21.      i=Malloc(space); // 分配结点
                22.      scanf("%c",&space[i].data); // 输入A的元素值
                23.      space[r].cur=i; // 插入到表尾
                24.      r=i;
                25.    }
                26.    scanf("%*c"); // %*c吃掉回车符
                27.    space[r].cur=0; // 尾结点的指针为空
                28.    printf("请输入集合B的元素(共%d个):",n);
                29.    for(j=1;j<=n;j++)
                30.    { // 依次输入B的元素,若不在当前表中,则插入,否则删除
                31.      scanf("%c",&b);
                32.      p=S;
                33.      k=space[S].cur; // k指向集合A中的第一个结点
                34.      while(k!=space[r].cur&&space[k].data!=b)
                35.      { // 在当前表中查找
                36.        p=k;
                37.        k=space[k].cur;
                38.      }
                39.      if(k==space[r].cur)
                40.      { // 当前表中不存在该元素,插入在r所指结点之后,且r的位置不变
                41.        i=Malloc(space);
                42.        space[i].data=b;
                43.        space[i].cur=space[r].cur;
                44.        space[r].cur=i;
                45.      }
                46.      else // 该元素已在表中,删除之
                47.      {
                48.        space[p].cur=space[k].cur;
                49.        Free(space,k);
                50.        if(r==k)
                51.          r=p; // 若删除的是尾元素,则需修改尾指针
                52.      }
                53.    }
                54.  }
                55.  void main()
                56.  {
                57.    int k;
                58.    SLinkList s;
                59.    difference(s,k);
                60.    ListTraverse(s,k,print2);
                61.  }
                 // algo2-7.cpp 教科书中图2.10静态链表示例
              1.  // 第1个结点的位置在[0].cur中。成员cur的值为0,则到链表尾
              2.  #include"c1.h"
              3.  #define N 6 // 字符串长度
              4.  typedef char ElemType[N];
              5.  #include"c2-3.h"
              6.  void main()
              7.  {
              8.    SLinkList s={{"",1},{"ZHAO",2},{"QIAN",3},{"SUN",4},{"LI",5},{"ZHOU",6},{"WU",7},{"ZHENG",8},{"WANG",0}}; // 教科书中图2.10(a)的状态
              9.    int i;
              10.    i=s[0].cur; // i指示第1个结点的位置
              11.    while(i)
              12.    { // 输出教科书中图2.10(a)的状态
              13.      printf("%s ",s[i].data); // 输出链表的当前值
              14.      i=s[i].cur; // 找到下一个
              15.    }
              16.    printf("/n");
              17.    s[4].cur=9; // 按教科书中图2.10(b)修改(在"LI"之后插入"SHI")
              18.    s[9].cur=5;
              19.    strcpy(s[9].data,"SHI");
              20.    s[6].cur=8; // 删除"ZHENG"
              21.    i=s[0].cur; // i指示第1个结点的位置
              22.    while(i)
              23.    { // 输出教科书中图2.10(b)的状态
              24.      printf("%s ",s[i].data); // 输出链表的当前值
              25.      i=s[i].cur; // 找到下一个
              26.    }
              27.    printf("/n");
              28.  }
               // algo2-6.cpp 利用无头结点的单链表结构处理教科书图2.1(学生健康登记表)
            1.  #include"c1.h"
            2.  #define NAMELEN 8 // 姓名最大长度
            3.  #define CLASSLEN 4 // 班级名最大长度
            4.  struct stud // 记录的结构
            5.  {
            6.    char name[NAMELEN+1]; // 包括'/0'
            7.    long num;
            8.    char sex;
            9.    int age;
            10.    char Class[CLASSLEN+1]; // 包括'/0'
            11.    int health;
            12.  };
            13.  typedef stud ElemType; // 链表结点元素类型为结构体
            14.  #include"c2-2.h"
            15.  #include"bo2-8.cpp" // 无头结点单链表的部分基本操作
            16.  #include"func2-1.cpp" // 无头结点单链表的扩展操作
            17.  char sta[3][9]={"健康  ","一般  ","神经衰弱"}; // 健康状况(3类)
            18.  FILE *fp; // 全局变量
            19.  void Print(stud e)
            20.  { // 显示记录e的内容
            21.    printf("%-8s %6ld",e.name,e.num);
            22.    if(e.sex=='m')
            23.      printf(" 男");
            24.    else
            25.      printf(" 女");
            26.    printf("%5d  %-4s",e.age,e.Class);
            27.    printf("%9s/n",sta[e.health]);
            28.  }
            29.  void ReadIn(stud &e)
            30.  { // 由键盘输入结点信息
            31.    printf("请输入姓名(<=%d个字符): ",NAMELEN);
            32.    scanf("%s",e.name);
            33.    printf("请输入学号: ");
            34.    scanf("%ld",&e.num);
            35.    printf("请输入性别(m:男 f:女): ");
            36.    scanf("%*c%c",&e.sex);
            37.    printf("请输入年龄: ");
            38.    scanf("%d",&e.age);
            39.    printf("请输入班级(<=%d个字符): ",CLASSLEN);
            40.    scanf("%s",e.Class);
            41.    printf("请输入健康状况(0:%s 1:%s 2:%s):",sta[0],sta[1],sta[2]);
            42.    scanf("%d",&e.health);
            43.  }
            44.  void WriteToFile(stud e)
            45.  { // 将结点信息写入fp指定的文件
            46.    fwrite(&e,sizeof(stud),1,fp);
            47.  }
            48.  Status ReadFromFile(stud &e)
            49.  { // 由fp指定的文件读取结点信息到e
            50.    int i;
            51.    i=fread(&e,sizeof(stud),1,fp);
            52.    if(i==1) // 读取文件成功
            53.      return OK;
            54.    else
            55.      return ERROR;
            56.  }
            57.  int cmp(ElemType c1,ElemType c2)
            58.  {
            59.    return (int)(c1.num-c2.num);
            60.  }
            61.  void Modify(LinkList &L,ElemType e)
            62.  { // 修改结点内容,并按学号将结点非降序插入链表L
            63.    char s[80];
            64.    Print(e); // 显示原内容
            65.    printf("请输入待修改项的内容,不修改的项按回车键保持原值:/n");
            66.    printf("请输入姓名(<=%d个字符): ",NAMELEN);
            67.    gets(s);
            68.    if(strlen(s))
            69.      strcpy(e.name,s);
            70.    printf("请输入学号: ");
            71.    gets(s);
            72.    if(strlen(s))
            73.      e.num=atol(s);
            74.    printf("请输入性别(m:男 f:女): ");
            75.    gets(s);
            76.    if(strlen(s))
            77.      e.sex=s[0];
            78.    printf("请输入年龄: ");
            79.    gets(s);
            80.    if(strlen(s))
            81.      e.age=atoi(s);
            82.    printf("请输入班级(<=%d个字符): ",CLASSLEN);
            83.    gets(s);
            84.    if(strlen(s))
            85.      strcpy(e.Class,s);
            86.    printf("请输入健康状况(0:%s 1:%s 2:%s):",sta[0],sta[1],sta[2]);
            87.    gets(s);
            88.    if(strlen(s))
            89.      e.health=atoi(s); // 修改完毕
            90.    InsertAscend(L,e,cmp); // 把q所指结点的内容按学号非降序插入L(func2-1.cpp)
            91.  }
            92.  #define N 4 // student记录的个数
            93.  Status EqualNum(ElemType c1,ElemType c2)
            94.  {
            95.    if(c1.num==c2.num)
            96.      return OK;
            97.    else
            98.      return ERROR;
            99.  }
            100.  Status EqualName(ElemType c1,ElemType c2)
            101.  {
            102.    if(strcmp(c1.name,c2.name))
            103.      return ERROR;
            104.    else
            105.      return OK;
            106.  }
            107.  void main()
            108.  { // 表的初始记录
            109.    stud student[N]={{"王小林",790631,'m',18,"计91",0},{"陈红",790632,'f',20,"计91",1},
            110.             {"刘建平",790633,'m',21,"计91",0},{"张立立",790634,'m',17,"计91",2}};
            111.    int i,j,flag=1;
            112.    char filename[13];
            113.    ElemType e;
            114.    LinkList T,p,q;
            115.    InitList(T); // 初始化链表
            116.    while(flag)
            117.    {
            118.      printf("1:将结构体数组student中的记录按学号非降序插入链表/n");
            119.      printf("2:将文件中的记录按学号非降序插入链表/n");
            120.      printf("3:键盘输入新记录,并将其按学号非降序插入链表/n");
            121.      printf("4:删除链表中第一个有给定学号的记录/n");
            122.      printf("5:删除链表中第一个有给定姓名的记录/n");
            123.      printf("6:修改链表中第一个有给定学号的记录/n");
            124.      printf("7:修改链表中第一个有给定姓名的记录/n");
            125.      printf("8:查找链表中第一个有给定学号的记录/n");
            126.      printf("9:查找链表中第一个有给定姓名的记录/n");
            127.      printf("10:显示所有记录 11:将链表中的所有记录存入文件 12:结束/n");
            128.      printf("请选择操作命令: ");
            129.      scanf("%d",&i);
            130.      switch(i)
            131.      {
            132.        case 1: for(j=0;j<N;j++)
            133.          InsertAscend(T,student[j],cmp); // 在func2-1.cpp中
            134.            break;
            135.        case 2: printf("请输入文件名: ");
            136.            scanf("%s",filename);
            137.            if((fp=fopen(filename,"rb"))==NULL)
            138.          printf("打开文件失败!/n");
            139.            else
            140.            {
            141.          while(ReadFromFile(e))
            142.            InsertAscend(T,e,cmp); // 在func2-1.cpp中
            143.          fclose(fp);
            144.            }
            145.            break;
            146.        case 3: ReadIn(e);
            147.            InsertAscend(T,e,cmp); // 在func2-1.cpp中
            148.            break;
            149.        case 4: printf("请输入待删除记录的学号: ");
            150.            scanf("%ld",&e.num);
            151.            if(!DeleteElem(T,e,EqualNum)) // 在func2-1.cpp中
            152.          printf("没有学号为%ld的记录/n",e.num);
            153.            break;
            154.        case 5: printf("请输入待删除记录的姓名: ");
            155.            scanf("%*c%s",e.name); // %*c吃掉回车符
            156.            if(!DeleteElem(T,e,EqualName)) // 在func2-1.cpp中
            157.          printf("没有姓名为%s的记录/n",e.name);
            158.            break;
            159.        case 6: printf("请输入待修改记录的学号: ");
            160.            scanf("%ld%*c",&e.num);
            161.            if(!DeleteElem(T,e,EqualNum)) // 在链表中删除该结点,并由e返回(在func2-1.cpp)
            162.          printf("没有学号为%ld的记录/n",e.num);
            163.            else
            164.          Modify(T,e); // 修改e并按学号插入链表T
            165.            break;
            166.        case 7: printf("请输入待修改记录的姓名: ");
            167.            scanf("%*c%s%*c",e.name); // %*c吃掉回车符
            168.            if(!DeleteElem(T,e,EqualName)) // 在func2-1.cpp中
            169.          printf("没有姓名为%s的记录/n",e.name);
            170.            else
            171.          Modify(T,e);
            172.            break;
            173.        case 8: printf("请输入待查找记录的学号: ");
            174.            scanf("%ld",&e.num);
            175.            if(!(q=Point(T,e,EqualNum,p))) // 在func2-1.cpp中
            176.          printf("没有学号为%ld的记录/n",e.num);
            177.            else
            178.          Print(q->data);
            179.            break;
            180.        case 9: printf("请输入待查找记录的姓名: ");
            181.            scanf("%*c%s",e.name);
            182.            if(!(q=Point(T,e,EqualName,p))) // 在func2-1.cpp中
            183.          printf("没有姓名为%s的记录/n",e.name);
            184.            else
            185.          Print(q->data);
            186.            break;
            187.        case 10:printf("  姓名    学号 性别 年龄 班级 健康状况/n");
            188.            ListTraverse(T,Print);
            189.            break;
            190.        case 11:printf("请输入文件名: ");
            191.            scanf("%s",filename);
            192.            if((fp=fopen(filename,"wb"))==NULL)
            193.          printf("打开文件失败!/n");
            194.            else
            195.          ListTraverse(T,WriteToFile);
            196.            fclose(fp);
            197.            break;
            198.        case 12:flag=0;
            199.      }
            200.    }
            201.  }
             // algo2-5.cpp 实现算法2.11、2.12的程序
          1.  #include"c1.h"
          2.  typedef int ElemType;
          3.  #include"c2-2.h"
          4.  #include"bo2-2.cpp"
          5.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
          6.  void CreateList(LinkList &L,int n) // 算法2.11
          7.  { // 逆位序(插在表头)输入n个元素的值,建立带表头结构的单链线性表L
          8.    int i;
          9.    LinkList p;
          10.    L=(LinkList)malloc(sizeof(LNode));
          11.    L->next=NULL; // 先建立一个带头结点的单链表
          12.    printf("请输入%d个数据/n",n);
          13.    for(i=n;i>0;--i)
          14.    {
          15.      p=(LinkList)malloc(sizeof(LNode)); // 生成新结点
          16.      scanf("%d",&p->data); // 输入元素值
          17.      p->next=L->next; // 插入到表头
          18.      L->next=p;
          19.    }
          20.  }
          21.  void CreateList2(LinkList &L,int n)
          22.  { // 正位序(插在表尾)输入n个元素的值,建立带表头结构的单链线性表L
          23.    int i;
          24.    LinkList p,q;
          25.    L=(LinkList)malloc(sizeof(LNode)); // 生成头结点
          26.    L->next=NULL;
          27.    q=L;
          28.    printf("请输入%d个数据/n",n);
          29.    for(i=1;i<=n;i++)
          30.    {
          31.      p=(LinkList)malloc(sizeof(LNode));
          32.      scanf("%d",&p->data);
          33.      q->next=p;
          34.      q=q->next;
          35.    }
          36.    p->next=NULL;
          37.  }
          38.  void MergeList(LinkList La,LinkList &Lb,LinkList &Lc) // 算法2.12
          39.  { // 已知单链线性表La和Lb的元素按值非递减排列。
          40.    // 归并La和Lb得到新的单链线性表Lc,Lc的元素也按值非递减排列
          41.    LinkList pa=La->next,pb=Lb->next,pc;
          42.    Lc=pc=La; // 用La的头结点作为Lc的头结点
          43.    while(pa&&pb)
          44.      if(pa->data<=pb->data)
          45.      {
          46.        pc->next=pa;
          47.        pc=pa;
          48.        pa=pa->next;
          49.      }
          50.      else
          51.      {
          52.        pc->next=pb;
          53.        pc=pb;
          54.        pb=pb->next;
          55.      }
          56.    pc->next=pa?pa:pb; // 插入剩余段
          57.    free(Lb); // 释放Lb的头结点
          58.    Lb=NULL;
          59.  }
          60.  void main()
          61.  {
          62.    int n=5;
          63.    LinkList La,Lb,Lc;
          64.    printf("按非递减顺序, ");
          65.    CreateList2(La,n); // 正位序输入n个元素的值
          66.    printf("La="); // 输出链表La的内容
          67.    ListTraverse(La,print);
          68.    printf("按非递增顺序, ");
          69.    CreateList(Lb,n); // 逆位序输入n个元素的值
          70.    printf("Lb="); // 输出链表Lb的内容
          71.    ListTraverse(Lb,print);
          72.    MergeList(La,Lb,Lc); // 按非递减顺序归并La和Lb,得到新表Lc
          73.    printf("Lc="); // 输出链表Lc的内容
          74.    ListTraverse(Lc,print);
          75.  }
           // algo2-4.cpp 修改算法2.7的第一个循环语句中的条件语句为开关语句,且当
        1.  // *pa=*pb时,只将两者中之一插入Lc。此操作的结果和算法2.1相同
        2.  #include"c1.h"
        3.  typedef int ElemType;
        4.  #include"c2-1.h"
        5.  #include"bo2-1.cpp"
        6.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
        7.  void MergeList(SqList La,SqList Lb,SqList &Lc)
        8.  { // 另一种合并线性表的方法(根据算法2.7下的要求修改算法2.7),La、Lb和Lc均为按递增排列的表
        9.    ElemType  *pa,*pa_last,*pb,*pb_last,*pc;
        10.    pa=La.elem;
        11.    pb=Lb.elem;
        12.    Lc.listsize=La.length+Lb.length; // 此句与算法2.7不同
        13.    pc=Lc.elem=(ElemType *)malloc(Lc.listsize*sizeof(ElemType));
        14.    if(!Lc.elem)
        15.      exit(OVERFLOW);
        16.    pa_last=La.elem+La.length-1;
        17.    pb_last=Lb.elem+Lb.length-1;
        18.    while(pa<=pa_last&&pb<=pb_last) // 表La和表Lb均非空
        19.      switch(comp(*pa,*pb)) // 此句与算法2.7不同
        20.      {
        21.        case  0: pb++;
        22.        case -1: *pc++=*pa++;
        23.         break;
        24.        case  1: *pc++=*pb++;
        25.      }
        26.    while(pa<=pa_last) // 表La非空且表Lb空
        27.      *pc++=*pa++;
        28.    while(pb<=pb_last) // 表Lb非空且表La空
        29.      *pc++=*pb++;
        30.    Lc.length=pc-Lc.elem; // 加此句
        31.  }
        32.  void main()
        33.  {
        34.    SqList La,Lb,Lc;
        35.    int j;
        36.    InitList(La); // 创建空表La
        37.    for(j=1;j<=5;j++) // 在表La中插入5个元素,依次为1、2、3、4、5
        38.      ListInsert(La,j,j);
        39.    printf("La= "); // 输出表La的内容
        40.    ListTraverse(La,print1);
        41.    InitList(Lb); // 创建空表Lb
        42.    for(j=1;j<=5;j++) // 在表Lb中插入5个元素,依次为2、4、6、8、10
        43.      ListInsert(Lb,j,2*j);
        44.    printf("Lb= "); // 输出表Lb的内容
        45.    ListTraverse(Lb,print1);
        46.    MergeList(La,Lb,Lc); // 由按递增排列的表La、Lb得到按递增排列的表Lc
        47.    printf("Lc= "); // 输出表Lc的内容
        48.    ListTraverse(Lc,print1);
        49.  }
         // algo2-3.cpp 实现算法2.7的程序
      1.  #include"c1.h"
      2.  typedef int ElemType;
      3.  #include"c2-1.h"
      4.  #include"bo2-1.cpp"
      5.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
      6.  void MergeList(SqList La,SqList Lb,SqList &Lc) // 算法2.7
      7.  { // 已知顺序线性表La和Lb的元素按值非递减排列。
      8.    // 归并La和Lb得到新的顺序线性表Lc,Lc的元素也按值非递减排列
      9.    ElemType *pa,*pa_last,*pb,*pb_last,*pc;
      10.    pa=La.elem;
      11.    pb=Lb.elem;
      12.    Lc.listsize=Lc.length=La.length+Lb.length; // 不用InitList()创建空表Lc
      13.    pc=Lc.elem=(ElemType *)malloc(Lc.listsize*sizeof(ElemType));
      14.    if(!Lc.elem) // 存储分配失败
      15.      exit(OVERFLOW);
      16.    pa_last=La.elem+La.length-1;
      17.    pb_last=Lb.elem+Lb.length-1;
      18.    while(pa<=pa_last&&pb<=pb_last) // 表La和表Lb均非空
      19.    { // 归并
      20.      if(*pa<=*pb)
      21.        *pc++=*pa++; // 将pa所指单元的值赋给pc所指单元后,pa和pc分别+1(指向下一个单元)
      22.      else
      23.        *pc++=*pb++; // 将pb所指单元的值赋给pc所指单元后,pa和pc分别+1(指向下一个单元)
      24.    } // 以下两个while循环只会有一个被执行
      25.    while(pa<=pa_last) // 表La非空且表Lb空
      26.      *pc++=*pa++; // 插入La的剩余元素
      27.    while(pb<=pb_last) // 表Lb非空且表La空
      28.      *pc++=*pb++; // 插入Lb的剩余元素
      29.  }
      30.  void main()
      31.  {
      32.    SqList La,Lb,Lc;
      33.    int j;
      34.    InitList(La); // 创建空表La
      35.    for(j=1;j<=5;j++) // 在表La中插入5个元素,依次为1、2、3、4、5
      36.      ListInsert(La,j,j);
      37.    printf("La= "); // 输出表La的内容
      38.    ListTraverse(La,print1);
      39.    InitList(Lb); // 创建空表Lb
      40.    for(j=1;j<=5;j++) // 在表Lb中插入5个元素,依次为2、4、6、8、10
      41.      ListInsert(Lb,j,2*j);
      42.    printf("Lb= "); // 输出表Lb的内容
      43.    ListTraverse(Lb,print1); // 由按非递减排列的表La、Lb得到按非递减排列的表Lc
      44.    MergeList(La,Lb,Lc);
      45.    printf("Lc= "); // 输出表Lc的内容
      46.    ListTraverse(Lc,print1);
      47.  }
       // algo2-2.cpp 实现算法2.2的程序
    1.  #include"c1.h"
    2.  typedef int ElemType;
    3.  #include"c2-1.h"
    4.  #include"bo2-1.cpp"
    5.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
    6.  void MergeList(SqList La,SqList Lb,SqList &Lc) // 算法2.2
    7.  { // 已知线性表La和Lb中的数据元素按值非递减排列。
    8.    // 归并La和Lb得到新的线性表Lc,Lc的数据元素也按值非递减排列
    9.    int i=1,j=1,k=0;
    10.    int La_len,Lb_len;
    11.    ElemType ai,bj;
    12.    InitList(Lc); // 创建空表Lc
    13.    La_len=ListLength(La);
    14.    Lb_len=ListLength(Lb);
    15.    while(i<=La_len&&j<=Lb_len) // 表La和表Lb均非空
    16.    {
    17.      GetElem(La,i,ai);
    18.      GetElem(Lb,j,bj);
    19.      if(ai<=bj)
    20.      {
    21.        ListInsert(Lc,++k,ai);
    22.        ++i;
    23.      }
    24.      else
    25.      {
    26.        ListInsert(Lc,++k,bj);
    27.        ++j;
    28.      }
    29.    } // 以下两个while循环只会有一个被执行
    30.    while(i<=La_len) // 表La非空且表Lb空
    31.    {
    32.      GetElem(La,i++,ai);
    33.      ListInsert(Lc,++k,ai);
    34.    }
    35.    while(j<=Lb_len) // 表Lb非空且表La空
    36.    {
    37.      GetElem(Lb,j++,bj);
    38.      ListInsert(Lc,++k,bj);
    39.    }
    40.  }
    41.  void main()
    42.  {
    43.    SqList La,Lb,Lc;
    44.    int j,a[4]={3,5,8,11},b[7]={2,6,8,9,11,15,20};
    45.    InitList(La); // 创建空表La
    46.    for(j=1;j<=4;j++) // 在表La中插入4个元素
    47.      ListInsert(La,j,a[j-1]);
    48.    printf("La= "); // 输出表La的内容
    49.    ListTraverse(La,print1);
    50.    InitList(Lb); // 创建空表Lb
    51.    for(j=1;j<=7;j++) // 在表Lb中插入7个元素
    52.      ListInsert(Lb,j,b[j-1]);
    53.    printf("Lb= "); // 输出表Lb的内容
    54.    ListTraverse(Lb,print1);
    55.    MergeList(La,Lb,Lc);
    56.    printf("Lc= "); // 输出表Lc的内容
    57.    ListTraverse(Lc,print1);
    58.  }
     // algo2-1.cpp 实现算法2.1的程序
  1.  #include"c1.h"
  2.  #include"c2-1.h" // 采用线性表的动态分配顺序存储结构
  3.  #include"bo2-1.cpp" // 可以使用bo2-1.cpp中的基本操作
  4.  #include"func2-3.cpp" // 包括equal()、comp()、print()、print2()和print1()函数
  5.  typedef int ElemType;
  6.  void Union(SqList &La,SqList Lb) // 算法2.1
  7.  { // 将所有在线性表Lb中但不在La中的数据元素插入到La中
  8.    ElemType e;
  9.    int La_len,Lb_len;
  10.    int i;
  11.    La_len=ListLength(La); // 求线性表的长度
  12.    Lb_len=ListLength(Lb);
  13.    for(i=1;i<=Lb_len;i++)
  14.    {
  15.      GetElem(Lb,i,e); // 取Lb中第i个数据元素赋给e
  16.      if(!LocateElem(La,e,equal)) // La中不存在和e相同的元素,则插入之
  17.        ListInsert(La,++La_len,e);
  18.    }
  19.  }
  20.  void main()
  21.  {
  22.    SqList La,Lb;
  23.    int j;
  24.    InitList(La); // 创建空表La。如不成功,则会退出程序的运行
  25.    for(j=1;j<=5;j++) // 在表La中插入5个元素,依次为1、2、3、4、5
  26.      ListInsert(La,j,j);
  27.    printf("La= "); // 输出表La的内容
  28.    ListTraverse(La,print1);
  29.    InitList(Lb); // 创建空表Lb
  30.    for(j=1;j<=5;j++) // 在表Lb中插入5个元素,依次为2、4、6、8、10
  31.      ListInsert(Lb,j,2*j);
  32.    printf("Lb= "); // 输出表Lb的内容
  33.    ListTraverse(Lb,print1);
  34.    Union(La,Lb); // 调用Union(),将Lb中满足条件的元素插入La
  35.    printf("new La= "); // 输出新表La的内容
  36.    ListTraverse(La,print1);
  37.  }

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值