C++技术支持作业范例:有关动态链表的经典例题

/* (程序头部注释开始) * 程序的版权和版本声明部分 * Copyright (c) 2011, 烟台大学计算机学院学生 * All rights reserved. * 文件名称:  有关动态链表的经典例题                          * 作    者:李洪悬                              * 完成日期:   2012      年 4   月  4     日 * 版 本 号:         

* 对任务及求解方法的描述部分 * 输入描述: * 问题描述: * 程序输出: * 程序头部的注释结束 */

#include <stdio.h>

#include <malloc.h> #define MAXSIZE 100 #define TRUE 1 #define FALSE 0 #define OK 1 #define ERROR 0 #define OVERFLOW -2 #define NULL 0 struct LNode { int data; struct LNode * next; }; typedef LNode * Link, * Position, Node; struct LLink { Link head, tail; int len; }; typedef LLink LinkList; //创建一个结点,其值为value。 int MakeNode(Link &p, int value) { //p = (Link) malloc(sizeof(Node)); p = (LNode * ) malloc(sizeof(Node)); if (p == NULL) { return ERROR; } p->data = value; p->next = NULL; return OK; } //释放p所指向的结点。 void FreeNode(Link &p) { free(p); p = NULL; } //构造一个空的线性链表L。 int InitList(LinkList &L) { L.head = NULL; L.tail = NULL; L.len = 0; return OK; } //已知h指向线性链表L的第一个结点,将s所指结点插入到h之前。 int InsFirst(LinkList &L, Link h, Link s) { if (s == NULL) { return ERROR; } s->next = h; L.head = s; if (L.tail == NULL) { L.tail = s; } L.len++; return OK; } //删除线性链表L中的第一个结点,并以q返回。 int DelFirst(LinkList &L, Link &q) { if (L.head == NULL) { return ERROR; } q = L.head; L.head = q->next; if (q == L.tail) { L.head = NULL; L.tail = NULL; } L.len--; return OK; } //将指针s所指的一串结点链接在线性表L的尾部。 int Append(LinkList &L, Link s) { if (s == NULL) { return ERROR; } L.tail->next = s; L.len++; while(s->next != NULL) { s = s->next; L.len++; } L.tail = s; return OK; } //删除线性链表L中的尾结点并以q返回。 int Remove(LinkList &L, Link &q) { if (L.len == 0) { return ERROR; } Link p; p = L.head; while (p->next != L.tail) { p = p->next; } q = p->next; p->next = NULL; L.tail = p; L.len--; return OK; } //返回p指示线性链表L中第i个结点的位置,并返回OK,i值不合法时返回ERROR。 int LocatePos(LinkList L, int i, Link &p) { int j; if (i < 0 || i > L.len) { return ERROR; } p = L.head; for (j = 1; j < i; j++) { p = p->next; } return OK; } //已知p指向线性链表L中的一个结点,返回p所指结点的直接前驱的位置。若无直接前驱,则返回NULL。 Position PriorPos(LinkList L, Link p) { if (p == L.head->next) { return NULL; } Link q; q = L.head->next; while (q->next != p) { q = q->next; } return q; } //已知p指向线性链表L中的一个结点,返回p所指结点的直接后继的位置。若无直接后继,则返回NULL。 Position NextPos(LinkList L, Link p) { if (p->next == NULL) { return NULL; } return p->next; } //已知p指向线性链表L中的一个结点,将s所指结点插入在p所指结点之前。 int InsBefore(LinkList &L, Link &p, Link s) { if (s == NULL || p == NULL) { return NULL; } Link q; q = PriorPos(L, p); if (q == NULL) { q = L.head; } q->next = s; s->next = p; //p = s; L.len++; return OK; } //已知p指向线性链表L中的一个结点,将s所指结点插入在p所指结点之后。 int InsAfter(LinkList &L, Link &p, Link s) { if (s == NULL || p == NULL) { return NULL; } if (p == L.tail) { L.tail = s; } s->next = p->next; p->next = s; L.len++; return OK; } //返回线性链表L中头结点的位置。 Position GetHead(LinkList L) { return L.head; } //返回线性链表L中尾结点的位置。 Position GetLast(LinkList L) { return L.tail; } //释放线性链表L。 int FreeList(LinkList &L) { if (L.len == 0) { return OK; } Link p, q; p = GetHead(L); while (p != NULL) { q = p; p = p->next; free(q); } L.head = NULL; L.tail = NULL; L.len = 0; return OK; } //输出线性链表L中的各个结点,并输出头尾指针所指元素值。 int Display(LinkList L) { int i; if (L.head == NULL) { return ERROR; } Link p = L.head; for (i = 1; i <= L.len; i++) { printf("%d ", p->data); p = p->next; } printf("\n"); printf("head value : %d \n", L.head->data); printf("tail value : %d \n", L.tail->data); printf("\n"); return OK; } int main() { int i; Link p; Link q; LinkList La, Lb; //初始化线性链表La。 if (!InitList(La)) { return OVERFLOW; } for (i = 7; i >= 1; i = i -1) { MakeNode(p, i); InsFirst(La, La.head, p); } printf("链表La为:"); Display(La); //初始化线性链表Lb。 if (!InitList(Lb)) { return OVERFLOW; } for (i = 17; i >= 11; i = i -1) { MakeNode(p, i); InsFirst(Lb, Lb.head, p); } printf("链表Lb为:"); Display(Lb); //将链表Lb链接到链表La之后。 printf("两个线性链表想链接La + Lb: \n"); Append(La, Lb.head); Display(La); //删除首结点。 DelFirst(La, q); printf("被删除的首结点值为:%d\n", q->data); FreeNode(q); Display(La); //删除尾结点。 Remove(La, q); printf("删除链表L中的最后一个结点:%d\n",q->data); FreeNode(q); Display(La); //定位第六个元素结点,并用p指针指向该结点。 LocatePos(La, 6, p); Display(La); printf("第六个元素结点数据:%d\n",p->data); //p结点的直接前驱。 q = PriorPos(La, p); Display(La); printf("第六个元素结点数据:%d\n",p->data); printf("第六个元素结点的直接前驱数据是:%d\n",q->data); //p结点的直接后继。 q = NextPos(La, p); Display(La); printf("第六个元素结点数据:%d\n",p->data); printf("第六个元素结点的直接后继数据是:%d\n",q->data); printf("\n"); //在第六个结点前插入值为111的新结点。 printf("在第六个结点前插入值为111的新结点。\n"); MakeNode(q, 111); InsBefore(La, p, q); Display(La); //在原第六个结点后插入值为222的新结点。 printf("在原第六个结点后插入值为222的新结点。\n"); MakeNode(q, 222); InsAfter(La, p, q); Display(La); //输出线性链表La的表头结点。 q = GetHead(La); printf("线性链表La中表头结点的值为:%d\n",q->data); //输出线性链表La的表尾结点。 q = GetLast(La); printf("线性链表La中表尾结点的值为:%d\n",q->data); FreeList(La); Display(La); return 0; }


经验积累:链表是个好东西!要搞懂它!

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值