顺序表
- 数组实现,存储空间是连续的
- 随机存取,查找随机,增删要整体移动
定义
顺序表定义的三个要素
- 底层数组的首地址
- 存储空间的最大值(一开始就定了)
*数组的长度(随机变化的)
#define MAXSIZE 100;
typedef struct {
Elemtype * elem; //存储空间的地址
int length; //当前的长度
}SqList;
初始化
为顺序表动态分配一个预定义大小的存储空间,使elem指向该存储空间
将表长置零
status InitList(SqList &L)
{
L.elem = new Elemtype[MAXSIZE];
if (L.elem == NULL)
{
return ERROR; //存储空间申请失败
}
L.length = 0;
return OK;
}
取值
- 根据指定的位置,取得表中的值
- 判断给定的位置是否合法
- 将取出的值获取
status GetElem(SqList L, int i, Elemtype & e)
{
if (i < 1 && i > L.length)
{
return ERROR;
}
e = L.elem[i - 1];
return OK;
}
插入
- 根据指定位置,插入一个元素
- 判断插入位置是否合法,不合法就抛出异常
- 判断表是否已经存满,存满就抛出异常
- 从最后一个元素开始遍历到指定位置,依次向后移动一个位置
- 将指定元素插入到指定位置
- 表长 +1
Status InsertList(SqList &L,int i , ElemType e)
{ if(i < 1 && i > L.length)
return ERROR;
if((L.length == MAXSIZE)
return ERROR;
for( int j = L.length-1; j >= i -1; j--)
{ L.elem[j+1] = L.elem[j];
}
elem[i-1] = e;
L.length++;
return OK;
}
删除
- 判断删除位置是否合法
- 把删除位置后的元素依次向前移动一位
- 表长-1
status DeleteList(SqList &L, int i )
{ if( i < 1 && i > L.length)
return ERROR;
for(int j = i -1 ; j < length; j++)
{ L.elem[j] = L.elem[j+1];
}
L.length --;
return OK;
}
查找
- 循环表,依次匹配要查找的元素
- 找到就返回位置+1
- 找不到就返回
Status LocateList(SqList &L, ElemType e)
{ for( int i = 0 ; i < L.length; i++)
{ if(e == L.elem[i])
return i + 1;
}
return 0 ;
}
单链表
- 底层是链表实现的,存储空间可以不连续
- 增删快,查改难,只能在表头进行查询
定义
- 链表名是头指针,指向头结点
- 头结点管理链表,指针域指向首元结点
- 结点有两个域,数据域以及指针域
- 先定义一个头结点,赋值给头指针
- 头结点的指针域置为NULL
typedef struct LNode {
ElemType data ;
struct LNode * next ;
} LNode , * LinkList
初始化
- 创建一个头结点,将指针赋值给头指针
- 将头结点的指针域置为NULL
status InitList (LinkList &L)
{
L = new LNode;
L-next = NULL;
return OK;
}
前插入法创建单链表
- 创建一个空链表
- 根据指定的元素个数进行结点前插
- 创建一个新的结点,对结点的数据域赋值,将结点插入到头结点后
status InitList_head(LinkList & L ,int i )
{ L = new LNode;
L->next = NULL;
for(int j = 1; j <= i; j++)
{ LNode * p = new LNode();
cin >> p -> data;
p ->next = L->next; //新的结点指向首元结点
L->next = p; //头结点指向新的新的结点,新结点成为首元结点
}
return OK;
}
后插入法创建新链表
- 创建一个空链表
- 创建一个尾指针指向头结点
- 根据指定的元素个数进行结点后插
- 创建一个新的结点,对结点的数据域赋值,将结点拼接到末结点
status InitList_end(LinkList &L ,int i)
{ L = new LNode;
L->next = NULL;
LNode * r;
r = L;
for( int j = 1; j < = i; j++)
{ LNode * p = new LNode;
cin >> p->data;
p ->next = NULL;
r ->next = p; //将p插入到位置
r = p; //将指针重新指向最后一个结点
}
return OK;
}
插入元素
- 在指定位置i 插入一个新的结点
- 创建一个新的结点指针p,初始化为头指针
- 创建一个新的结点s,结点的指针域赋值为指定值
- 创建一个计数器;
- 从表头遍历链表,找到了指定位置,将结点a的指针赋值给结点指针p
- 将 结点s指针域指向 结点 b ,再将结点a的指针域指向结点s
status InsertList(LinkList &L,int i, ElemType e)
{
LNode * p ;
p = L;
int j = 0; //计数器
while( p && j < i - 1)
{ p = p ->next;
j++;
}
if !p && j > i -1 )
return ERROR; //指定位置非法, i < 1 || i > n + 1 (为链表的元素个数)
LNode * s = new LNode;
s -> data = e;
s -> next = p ->next;
p -> next = s;
return OK;
}
取值
- 获取指定位置的元素
- 创建一个结点指针p,指向首元结点
- 创建一个计数器,初始化为1
- 遍历链表,查找指定的结点,循环条件(p不为NULL && j < i) ,循环体(p指向下一个指针,计数器加1)
- 如果指针为空或者指定位置不合法(i <1 | | i > n),查找失败,返回ERROR
- 查找成功则返回该元素
Status GetElem(LinkList lL, int i, ElemType &e)
{
LNode * p = L -> next;
int j = 1;
while( p && j < i)
{ p = p -> next;
j++;
}
if( !p || j > i)
return ERROR;
e = p -> data;
return OK;
}
查找
- 判断指定元素是否存在,存在泽返回它的地址,否则返回NULL
- 创建一个新的结点指针指向首元结点
- 遍历链表,查找元素,循环条件为(p 不为NULL && p->data != 要查找的元素)
- 返回当前的指针值,成功则返回指定元素的地址,失败则返回NULL
LNode * LocateList(LinkList L , ElemType e)
{ LNode * p = L->next;
while( p && p ->data != e)
{ p = p->next;
}
return p;
}
删除
- 根据指定的位置删除元素
- 创建结点指针p,初始化为头指针
- 遍历链表,指针p获取指定位置的前一个结点的指针,循环条件为(当前指针所指结点的指针域不为零 && 当前位置小与指定位置的前一个结点)
- 如果指定位置不合法则返回ERROR
- 找到指定位置结点,保存该结点的指针,以备释放
- 将指定位置前一个结点的指针域指向所找元素的下一个结点
- 释放被删除的结点的资源
Status DeleteList(LinkList &L, int i )
{ pNode * p = L;
int j = 0;
while ( (p -> next) && (j < i - 1) )
{ p = p -> next;
j++;
}
if( (p -> next) || j > i -1) // i < 1 || i > n
return ERROR;
LNode * q = p ->next; //获取要删除的元素的地址
p -> next = p ->next -> next;
delete q;
return OK;
}
单链表小项目练习
#pragma once
#include<iostream>
using namespace std;
#define OK 1;
#define ERROR 0;
//单链表的结点
typedef struct LNode
{
int data;
struct LNode * next; //结点的指针域
}LNode, *Linklist; // Linklist为指向结构体LNode的指针类型 ,定义数据类型
//单链表的初始化
/*
分析:
1,生成新节点作为头结点,用头指针L指向头结点
2,头结点的指针域置空
*/
bool InitList(Linklist &L)
{
L = new LNode; //1
L->next = NULL; //2
return OK;
}
//单链表的取值
/*
分析:
1,用指p指向首元结点,用j做计数器初始值赋为1
2,从首元结点开始依次向下访问,只要指向当前结点的指针域不为空,并且没有到达要寻找序号为i的结点,则循环继续执行操作:
(1)p指向下一个结点;
(2)计数器j加一
(3)退出循环时,如果指针p为空,或者计数器大于i,说明指定的序号i不合法,取值失败返回ERROR
若取值成功,此时j = i 时,p所指向的结点就时要找的第i个结点,用参数e 保存当前结点的数据域
返回OK
*/
//根据序号i,再链表中寻找元素的值,用e获取该元素的值
bool GetElem(Linklist L, int i, int &e) {
Linklist p = L->next;
int j = 1; //计数器
while (p && j < i) //循环停止条件:p为空或者指向第i个元素
{
p = p->next;
j++;
}
if (!p || j > i) //i值不合法
{
return ERROR;
}
e = p->data; //e接收i结点的数据域
return OK;
}
//根据相应元素查找
/*
分析:
1,用指针p指向首元结点
2,顺序查找,只要指向当前的指针p不为空,并且p所指结点的数据与不等于给定值,p就指向下一结点
3,返回p,若查找成功,返回该结点的地址值,若失败则返回NULL
*/
//再带有头结点的单链表中查询值为e的元素
LNode * LocateElem(Linklist L, int e) {
LNode * p;
p = L->next; // p指向首元结点
while (p && p->data != e)
{
p = p->next;
}
return p;
}
//单链表插入元素
/*
分析:
1,查找结点a,并由指针p指向该结点
2,生成一个新的结点变量*s
3,将结点变量*s的数据域置为e,
4,将新结点的指针与指向第i+1个结点
5,将结点变量*p的指针域指向新结点变量*s*/
//在带有头结点的单链表L第i个位置插入值为e的新结点
bool ListInsert(Linklist &L, int i, int e)
{
LNode * p;
p = L;
int j = 0; //计数器
while (p && (j < i - 1))
{
p = p->next;
j++;
}
if (!p || (j > i - 1)) //i < 1 或者 i > n + 1
{
return ERROR;
}
LNode *s = new LNode;
s->data = e;
s->next = p->next;
p->next = s;
return OK;
}
//单链表删除结点
/*
分析:
1,查找第i-1个系欸按,并让指针p指向该该节点
2,临时保存待删除结点的地址在q中,以备释放。
3,将结点*p的指针域指向第i个结点的直接后继结点
4,释放第i个结点的空间
*/
//删除单链表的第i个结点
bool ListDelete(Linklist &L, int i)
{
LNode *p = L;
int j = 0;
while ((p->next) && (j < i - 1)) //查找第i-1个结点,p指向该结点
{
p = p->next;
j++;
}
if ((p->next) || (j > i - 1)) //i<1 或者 i > n时,删除位置不合法
{
return ERROR;
}
Linklist q = p->next;
p->next = p->next->next;
delete q;
return OK;
}
//前插法创建单链表
/*
分析:
1,创建一个只有头结点的空链表
2,根据待创建的链表包含的元素个数执行多次插入操作
(1),生成一个新节点
(2),输入元素值赋给新节点*p的数据域
(3)将新结点*p插入到头结点之后
*/
//逆次序输入n个元素的值,建立带有表头结点的单链表L
bool CreateList_H(Linklist &L, int n)
{
L = new LNode;
L->next = NULL;
for (int i = 0; i < n; i++)
{
LNode *p = new LNode;
cout << "please input an id :" << endl;
cin >> p->data;
p->next = L->next;
L->next = p;
}
return OK;
}
//后插法创建单链表
/*
分析:
1,创建一个只有头结点的空链表
2,尾指针r初始化,指向头结点
3,根据创建链表包含的元素个数,循环n次操作:
(1)生成一个结点*p
(2)输入元素值,赋给新结点的数据域
(3)尾指针r指向新的尾结点*p
*/
//顺序输入n个元素的值
bool CreateList_R(Linklist &L, int n)
{
L = new LNode;
L->next = NULL; //创建一个带表头的单链表
LNode *r = L;
for ( int i = 0; i < n ; i++)
{
LNode *p = new LNode; //生成新节点
cout << "please input id " << endl;
cin >> p->data;
p->next = NULL;
r->next = p;//将新结点*p插入到尾结点之后
r = p; //将r指向新的尾节点
}
return OK;
}
//遍历单向链表
/*
1.获取链表的头结点并存储在指针*p中
2,循环操作 (循环结束条件p->next为空
(1)输出p->data数据域
(2)p指向下一个结点
*/
int TraverseList(Linklist L)
{
LNode * p = L->next; //指针指向头结点
int j = 0;
while (p) //下个结点不为空
{
j++;
cout << "第 " << j << " 元素为:" << p->data << endl;
p = p->next;
}
return j;
}
//修改元素
/*
1,接收键盘输入的修改值
2,顺序遍历链表,找到该值,并进行修改(循环条件是p ->next !=NULL)
3,修改成功返回true,修改失败返回false
*/
bool ChangeElem(Linklist &L, int e)
{
LNode * p = L->next;
int j = 1;
int value;
while (p != NULL)
{
if (p->data == e)
{
cout << "你要修改的元素在第" << j << " 个位置," << "请输入修改后的值:";
cin >> value;
p->data = value;
return OK;
}
p = p->next;
j++;
}
return false;
}
#include<iostream>
#include"Linklist.h"
using namespace std;
int main() {
Linklist L;
int flag3;
cout << "输入1创建空链表,输入2,前插法创建链表,输入3,后插法创建链表 \n";
cin >> flag3;
switch (flag3)
{
case 1:
{
if (InitList(L))
{
cout << "创建成功。" << endl;
}
break;
}
case 2:
{
int n;
cout << "请输入要输入的元素个数 :";
cin >> n;
if (CreateList_H(L, n))
{
cout << "创建成功。" << endl;
}
TraverseList(L);
break;
}
case 3:
{
int n;
cout << "请输入要输入的元素个数 :";
cin >> n;
if (CreateList_R(L, n))
{
cout << "创建成功。" << endl;
}
int total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
break;
}
default:
{
cout << "你的输入有误,默认后插法创建链表\n";
int n;
cout << "请输入要输入的元素个数 :";
cin >> n;
if (CreateList_R(L, n))
{
cout << "创建成功。" << endl;
}
int total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
break;
}
char flag = 'Y';
int flag2;
while (flag == 'y' || flag == 'Y')
{
cout << "输入4,插入元素,输入5,删除元素,输入6,查找元素,输入7,修改元素\n";
cin >> flag2;
switch (flag2)
{
case 4:
{ cout << "当前链表的信息为:" << endl;
int total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
int e;
cout << "请输入要插入的元素的值:\n";
cin >> e;
cout << "请输入要插入元素的位置 :\n";
int index;
cin >> index;
if (ListInsert(L, index, e))
{
cout << "插入元素成功。" << endl;
}
else
{
cout << "插入元素失败。" << endl;
}
cout << "修改后链表的信息为:" << endl;
total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
break;
}
case 5:
{
cout << "当前链表的信息为:" << endl;
int total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
cout << "请输入要插入元素的位置 :\n";
int index;
cin >> index;
if (ListDelete(L, index))
{
cout << "删除元素成功。" << endl;
}
else
{
cout << "删除元素失败。" << endl;
}
cout << "删除后链表的信息为:" << endl;
total = TraverseList(L);
cout << "链表总共有 " << total << " 个元素" << endl;
break;
}
case 6:
{
int e;
cout << "请输入要查找的元素的值:\n";
cin >> e;
LNode * address = LocateElem(L, e);
if (address != NULL)
{
cout << "该元素存在,在内存中的地址为" << address << endl;
}
else
{
cout << "该元素不存在。";
}
break;
}
case 7:
{
int e;
cout << "请输入你要进行修改的元素的值:";
cin >> e;
if (ChangeElem(L, e))
{
cout << "修改成功。" << endl << "修改后链表的值为" << endl;
TraverseList(L);
}
break;
}
default:
cout << "你的输入有误。" << endl;
break;
}
cout << "继续其他操作请输入Y/y,退出请输入N/n" << endl;
cin >> flag;
}
}
system("pause");
}
静态链表(了解)
- 用数组描述,游标实现法
- 一个数据域,一个游标
- 数组最后一个元素不存放数据,游标指向第一个有数据的元素(屁股指向头)
- 数组第一个元素不存放数据,游标指向第一个没有数据的元素(头指向尾)
定义
初始化
插入
- 根据游标指向下一个元素
- 最后一个元素右边是0
- 有数据元素的最后一个是空的,指向备用元素的第一个
循环链表
循环链表的前插入法
#include <iostream>
using namespace std;
#define OK true;
#define ERROR false;
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
int main(int argc, char** argv) {
cout << "helloworld";
return 0;
}
//循环链表定义
typedef struct pNode{
int data;
struct pNode *next;
} pNode,* LinkList;
//初始化:前插入法
bool InitList(LinkList &L,int n)
{
L = new pNode;
L->next = NULL;
pNode *p;
if(n != 0)
{
for(int i = 1;i <= n; i++ )
{
p = new pNode();
cin >> p->data;
p->next = L->next; //新的结点指向首元结点
L->next = p; //头结点指向新的新的结点,新结点成为首元结点
}
p -> next = L; //将最后一个结点的指针域指向头结点
}
return OK;
}
bool InsertList(LinkList &L, int i, int e)
{
pNode* p = L;
int j = 0;
while(p->next != L && j < i-1) //找到第i-1个结点
{
p = p -> next;
j++;
}
if( p == L && j < i -1 )
{
return ERROR ; //指定位置 < 1 || i < n-1(超出了链表的范围)
}
}
/*
>* 创建结点指针p,初始化为头指针
>* 遍历链表,指针p获取指定位置的前一个结点的指针,循环条件为(当前指针所指结点的指针域不为零 && 当前位置小与指定位置的前一个结点)
>* 如果指定位置不合法则返回ERROR
>* 找到指定位置结点,保存该结点的指针,以备释放
>* 将指定位置前一个结点的指针域指向所找元素的下一个结点
>* 释放被删除的结点的资源
*/
bool DeleteList(LinkList &L,int i)
{
int j = 0;
pNode *p = L;
while(p->next !=L && (j < i-1) )
{
p = p ->next;
j++;
}
if(p->next != L || j > i-1) // i < 1 || i > n
return ERROR;
pNode * q = p->next;
p->next = p->next->next;
delete q;
return OK;
}
循环链表的后插入法以及链表的合并
void Connect_List(LinkList &A, LinkList &B)
{
pNode * p1 = A;
pNode * p2 = B;
while (p1->next != A)
{
p1 = p->next;
}
while (p2->next != B)
{
p2 = p2->next;
}
pNode * temp;
temp = B->next->next; //获取第二个链表的首元结点
B->next = A->next;
A->next = p;
}
#include <iostream>
using namespace std;
#define OK true;
#define ERROR false;
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
//循环链表定义
typedef struct pNode {
int data;
struct pNode *next;
} pNode, *LinkList;
//初始化:尾插入法
pNode * InitList( int n)
{
pNode *head = new pNode();
pNode *p = head;
pNode * s = NULL;
if (n != 0)
{
for (int i = 1; i <= n; i++)
{
s = new pNode();
s->data = i;
p->next = s; //把新结点的指针赋值给当前的结点的指针域
p = s; // 获取最后一个结点的地址
}
s->next = head->next; //将最后一个结点的指针域指向头结点,形成一个环状
}
delete head;
return s->next; //返回首元结点的地址
}
int main(int argc, char** argv) {
int n = 41;
int m = 3;
pNode * p = InitList( n);
pNode * temp;
while (p != p->next){
for (int i = 1; i < m -1; i++) {
p = p->next;
}
cout << p->next->data << "->";
temp = p->next;
p->next = temp->next;
p = p->next;
}
cout << p->data;
system("pause");
return 0;
}
循环链表应用之魔术师发牌
// list_loop_connect.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
//循环链表定义
#include "pch.h"
#include<iostream>
using namespace std;
const int cardnumber = 13;
typedef struct pNode
{
int data;
struct pNode * next;
}pNode,* LinkList ;
void CreateList(LinkList &L,int n)
{
L = new pNode();
L->next = NULL;
pNode * r; //尾指针
r = L; //指向当前指针
for (int i = 1; i < cardnumber; i++)
{
pNode * p = new pNode();
p->data = 0;
p->next = NULL;
r->next = p; //将p拼接到最后的位置
r = p; //指针指向最后一个结点
}
r->next = L;
}
void InitList(LinkList &L)
{
pNode * p;
int j;
int cn = 2;
p = L; //指针指向首元结点
p->data = 1;
while (1)
{
for ( j = 0; j < cn; j++)
{
p = p->next;
if (p->data != 0)
{
//p = p->next;
j--;
}
}
if (p->data == 0)
{
p->data = cn;
cn++;
if (cn == 14)
{
break;
}
}
}
}
int main()
{
LinkList L;
CreateList(L, cardnumber);
InitList(L);
pNode * p = L;
while (p->next != L)
{
cout << p->data << "->";
p = p->next;
}
cout << p->data;
system("pause");
}
双链表
- 结点具有两个指针域,一个指向前驱结点,一个指向后驱结点
定义
tepedef struct DuLNode{
Elemtype data;
struct DuLNode * prior;
struct DuLNode * next;
} DuLNode ,*DuLinkList;
插入
bool ListInsert(DuLinkList &L, int i, Elemtype e)
{
DuNode * p;
if (! (p = GetElem(L, i)))
return ERROR;
DuNode * s = new DuNode;
s->data = e;
s->prior = p->prior;
p->prior->next = s;
s->next - p;
p->prior = s;
return OK;
}
删除`
bool Delete(DuLinkList &L, int i, )
{
DuNode * p;
if (! (p = GetElem(L, i)))
return ERROR;
p->prior->next = p ->next;
p->next->prior = p->prior;
delete p;
return OK;
}
双向链表实现代码
// double_list.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
#include "pch.h"
#include <iostream>
using namespace std;
const bool ERROR = false;
const bool OK = true;
//双向链表结点1
typedef struct DuNode
{
int data;
struct DuNode * prior;
struct DuNode * next;
}DuNode, * DuLinkList;
//在链表中特定的位置插入结点
DuLinkList GetElem(DuLinkList L, int i)
{
DuNode * p = L->next;
int j = 1;
while (p && j < i)
{
p = p->next;
j++;
}
if (!p || j > i)
return ERROR;
return p;
}
bool TraverseList(DuLinkList L)
{
if (L == NULL)
{
cout << "这是空链表。";
return ERROR;
}
DuNode * p = L ->next ;
int j = 0;
while (p)
{
j++;
cout << "第 " << j << " 个结点为 :" << p->data << endl;
p = p->next;
}
return OK;
}
bool Create_head(DuLinkList &L, int n)
{
L = new DuNode;
L->next = NULL;
L->prior = NULL;
if (L == NULL)
{
cout << "创建失败";
return ERROR;
}
DuNode * r = L; //尾指针
for (int j = 1; j <= n; j++)
{
DuNode * p = new DuNode;
if (p == NULL)
{
cout << "申请新结点失败。";
return ERROR;
}
cout << "请输入第 " << j << " 个结点的数据(整数0 - 32767) :";
cin >> p->data;
p->next = NULL;
p->prior = r;
r->next = p;
r = p;
}
cout << "创建成功" << endl;
return OK;
}
bool InsertNode(DuLinkList &L, int i, int e)
{
DuLinkList p;
if (!(p = GetElem(L, i)))
return NULL;
DuNode * s = new DuNode;
s->data = e;
s->next = p;
s->prior = p->prior;
p->prior->next = s;
p->next->prior = s;
cout << "插入成功,插入后的链表为:" << endl;
TraverseList(L);
return OK;
}
// 删除特定位置的结点
bool DeleteNode(DuLinkList &L, int i)
{
DuNode * p;
if (!(p = GetElem(L, i)))
return NULL;
p->prior->next = p->next;
p->next->prior = p->prior;
delete p;
cout << "删除成功,删除后的链表为:" << endl;
TraverseList(L);
return OK;
}
int main()
{
DuLinkList L;
Create_head(L, 10);
int exits = 1;
int flag = 3;
int index_in;
int index_out;
TraverseList(L);
while (flag != 0)
{
cout << "***********************************************************************************" << endl;
cout << "请输入要进行的操作,插入数据输入 1 ,删除数据输入 2 ,遍历链表输入 3 ,退出输入 0 :" << endl;
cout << "***********************************************************************************" << endl;
cin >> flag;
switch (flag)
{
case 2:
{
cout << "请输入要删除的结点的位置 :";
cin >> index_out;
DeleteNode(L, index_out);
break;
}
case 1:
{
int e;
cout << "请输入要添加的新节点的值 :";
cin >> e;
cout << endl;
cout << "请输入要插入新结点的位置 :";
cin >> index_in;
cout << endl;
InsertNode(L,index_in,e);
break;
}
case 3:
{
cout << "当前的链表的内容为 :" << endl;
TraverseList(L);
break;
}
case 0:
exits = 0;
break;
default:
cout << "你的输入有误。" << endl;
break;
}
}
return 0;
}
双向链表练习2
#include "pch.h"
#include <iostream>
using namespace std;
const int ERROR = 0;
const int OK = 1;
typedef char ElemType; //数据类型
typedef int Status; //返回码
typedef struct DualNode
{
ElemType data;
struct DualNode *prior;
struct DualNode *next;
}DualNode,* DuLinkList ;
Status InitList(DuLinkList &L) //尾插入法创建链表
{
DualNode * p, *q;
int i;
L = new DualNode; //头结点
if (L == NULL)
return ERROR;
L->next = NULL;
L->prior = NULL;
p = L; //尾指针
for (int i = 0; i < 26; i++)
{
q = new DualNode;
if (q == NULL)
{
cout << "申请新结点失败。";
return ERROR;
}
q->data = 65 + i;
q->prior = p;
q->next = NULL;
p->next = q;
p = q;
}
cout << "原链表为:" << endl;
DualNode * n= L->next;
while (n)
{
cout << n->data << " ";
n = n->next;
}
cout << endl;
p->next = L->next; //形成循环链表
L->next->prior = p;
return OK;
}
void Caesar(DuLinkList &L, int i)
{
if (i > 0)
{
do
{
L= L->next;
} while (--i);
}
if (i < 0)
{
do
{
L= L->next;
} while (++i);
}
}
int main()
{
DuLinkList L;
int n;
InitList(L);
cout << "请输入一个整数: ";
cin >> n;
cout << endl;
Caesar(L, n);
cout << "最终的链表:" << endl;
DualNode * p = L->next;
for (int i = 0; i < 26; i++)
{
cout << p->data << " ";
p = p->next;
}
return OK;
}
运行结果
原链表为:
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
请输入一个整数: 4
最终的链表:
E F G H I J K L M N O P Q R S T U V W X Y Z A B C D
原链表为:
A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
请输入一个整数: -2
最终的链表:
C D E F G H I J K L M N O P Q R S T U V W X Y Z A B