数据结构——单链表的基本操作

实验目的

通过该实验,深入理解链表的逻辑结构、物理结构等概念,掌握链表基本操作的编程实现,熟练掌握C语言中指针的操作。

实验内容

编程实现链表下教材第二章定义的线性表的基本操作,最好用菜单形式对应各个操作,使其编程一个完整的小软件。

参考界面:
在这里插入图片描述

源代码

#include <iostream>

using namespace std;

typedef int ElemType;
typedef struct LNode
{
    ElemType data;
    struct LNode *next;
}LNode,*LinkList;
//链表初始化
int InitList(LinkList &L)
{
    L=new LNode;
    if(!L) return 0;
    L->next=NULL;
    return 1;
}
//销毁链表
int DestoryList(LinkList &L)
{
    LinkList p;
    while(L)
    {
        p=L;
        L=L->next;
        delete p;
    }
    return 1;
}
//清空单链表
int ClearList(LinkList L)
{
    LinkList p,q;
    p=L->next;
    while(p){q=p;delete q;p=p->next;}
    L->next=NULL;
    return 1;
}
//求单链表长度
int Listlength(LinkList L)
{
    int sum=0;
    LinkList p=L->next;
    while(p)
    {
        p=p->next;
        sum++;
    }
    return sum;
}
//判断单链表是否为空
bool ListEmpty(LinkList L)
{
    if(L->next)
        return 1;
    else
        return 0;
}
//获取单链表中某个数据元素的内容
int GetElem(LinkList L,int i,ElemType &e)
{
    LinkList p=L->next;
    int j=1;
    while(p&&j<i)
    {
        p=p->next;
        ++j;
    }
    if(!p||j>i)return 0;
    e=p->data;
    return 1;
}
//查找值为e的数据元素的位置
int LocateElem(LinkList L,ElemType e)
{
    LinkList p=L->next;
    int i=0;
    while(p&&p->data!=e)
    {
        p=p->next;
        i++;
    }
    if(i>=Listlength(L))
        return 0;
    return i+1;
}
//求直接前驱
int PriorElem(LinkList L,ElemType e,ElemType&pre_e)
{
    LNode*p=L->next;
    if(e==p->data)
        return 0;
    while(p->next)
    {
        if(p->next->data==e)
        {
            pre_e=p->data;
            return 1;
        }
        p=p->next;
    }
    return 0;
}
//求直接后继
int NextElem(LinkList L,ElemType e,ElemType&next_e)
{
    LNode*p=L->next;
    while(p)
    {
        if(p->data==e&&p->next)
        {
            next_e=p->next->data;
            return 1;
        }
        p=p->next;
    }
    return 0;
}
//在单链表中插入数据元素
int ListInsert(LinkList&L,int i,ElemType e)
{
    LinkList p=L;
    int j=0;
    while(p&&(j<i-1))
    {
        p=p->next;
        ++j;
    }
    if(!p||j>i-1)return 0;
    LinkList s=new LNode;
    s->data=e;
    s->next=p->next;
    p->next=s;
    return 1;
}
//删除单链表中第i个元素,返回第i个元素的值
int ListDelete(LinkList &L,int i,ElemType&e)
{
    LinkList p=L;
    int j=0;
    while((p->next)&&(j<i-1))
    {
        p=p->next;
        ++j;
    }
    if(!(p->next)||(j>i-1)) return 0;
    LinkList q=p->next;
    e=q->data;
    p->next=q->next;
    delete q;
    return 1;
}
//输出链表元素
void LinkPrint(LinkList &L)
{
    LinkList p=L->next;
    while(p)
    {
        cout<<p->data<<" ";
        p=p->next;
    }
}
//前插法创建单链表
void CreateList_H(LinkList &L,int n)
{
    L=new LNode;
    L->next=NULL;
    cout<<"请输入要插入的元素:"<<endl;
    for(int i=0;i<n;i++)
    {
        LNode*p=new LNode;
        cin>>p->data;
        p->next=L->next;
        L->next=p;
    }
}
//后插法创建单链表
void CreateList_R(LinkList&L,int n)
{
    L=new LNode;
    L->next=NULL;
    LNode*r=L;
    for(int i=0;i<n;++i)
    {
        LinkList p=new LNode;
        cin>>p->data;
        p->next=NULL;
        r->next=p;
        r=p;
    }
}
//判断链表是否为空
bool IsEmpty(LinkList L)
{
    if(L->next)
        return false;
    else
        return true;
}
//链表逆转
int ReverseList(LinkList&L)
{
    if(L==NULL||L->next==NULL)
        return 0;
    LinkList pRev=NULL;
    LinkList pCur=L->next;
    while(pCur!=NULL)
    {
        LinkList temp=pCur;
        pCur=pCur->next;
        temp->next=pRev;
        pRev=temp;
    }
    L->next=pRev;
    return 1;
}
void PrintTips()
{
    cout<<"可执行的操作有:"<<endl;
    cout<<"********************"<<endl;
    cout<<"1.初始化或重置列表"<<endl;
    cout<<"2.销毁链表"<<endl;
    cout<<"3.链表中数据元素的个数"<<endl;
    cout<<"4.所指位序的元素值"<<endl;
    cout<<"5.链表已存在元素的位序"<<endl;
    cout<<"6.请输入元素,求直接前驱"<<endl;
    cout<<"7.请输入元素,求直接后继"<<endl;
    cout<<"8.在第i个位置插入元素"<<endl;
    cout<<"9.删除第i个元素"<<endl;
    cout<<"10.输出所输入的链表元素"<<endl;
    cout<<"11.初始化并输入链表元素"<<endl;
    cout<<"12.退出"<<endl;
    cout<<"13.判断单链表是否为空"<<endl;
    cout<<"14.链表逆转"<<endl;
    cout<<"********************"<<endl;
    cout<<"请输入你的选择:";
}
//判断输入是否合法
bool IsInvalid(LinkList L)
{
    if(L==NULL)
        {
            cout<<"链表未初始化!"<<endl;
            return true;
        }
    else
        return false;
}
int main()
{
    int k,s,i;
    ElemType e,res_e;
    LNode *p;
    LinkList L;
    PrintTips();
    while(cin>>k)
    {
        switch(k)
        {
        case 1:
            s=InitList(L);
            if(s==1)
                cout<<"初始化成功或重置成功!"<<endl;
            break;
        case 2:
            s=DestoryList(L);
            if(s==1)
                cout<<"销毁成功!"<<endl;
            break;
        case 3:
            if(IsInvalid(L)) break;
            s=Listlength(L);
            cout<<"链表中数据元素个数为:"<<s<<endl;
            break;
        case 4:
            if(IsInvalid(L)) break;
            if(!L->next)
            {
                cout<<"链表为空!"<<endl;
                break;
            }
            cout<<"请输入序号:";
            cin>>i;
            if(!GetElem(L,i,e))
            {
                cout<<"该位置超出链表范围!"<<endl;
                break;
            }
            cout<<"下标"<<i<<"处元素值为:"<<e<<endl;
            break;
        case 5:
            if(IsInvalid(L)) break;
            cout<<"请输入要查找的元素:";
            cin>>e;
            s=LocateElem(L,e);
            if(!s)
            {
                cout<<"不存在"<<endl;
                break;
            }
            cout<<"值为"<<e<<"的元素下标为:"<<s<<endl;
            break;
        case 6:
            if(IsInvalid(L)) break;
            if(!L->next)
            {
                cout<<"链表为空!"<<endl;
                break;
            }
            cout<<"请输入一个元素:";
            cin>>e;
            if(!PriorElem(L,e,res_e))
            {
                cout<<"查找失败!"<<endl;
                break;
            }
            cout<<"该元素的前驱为:"<<res_e<<endl;
            break;
        case 7:
            if(IsInvalid(L)) break;
            if(!L->next)
            {
                cout<<"链表为空!"<<endl;
                break;
            }
            cout<<"请输入一个元素:";
            cin>>e;
            if(!NextElem(L,e,res_e))
            {
                cout<<"查找失败!"<<endl;
                break;
            }
            cout<<"该元素的后继为:"<<res_e<<endl;
            break;
        case 8:
            if(IsInvalid(L)) break;
            cout<<"请输入要插入的位置和元素:";
            cin>>i>>e;
            s=ListInsert(L,i,e);
            if(s)
                cout<<"插入成功!"<<endl;
            else
                cout<<"插入失败!"<<endl;
            break;
        case 9:
            if(IsInvalid(L)) break;
            cout<<"请输入要删除的位置:";
            cin>>i;
            s=ListDelete(L,i,e);
            if(s)
                cout<<"删除成功!,该位置值为:"<<e<<endl;
            else
                cout<<"删除失败!"<<endl;
            break;
        case 10:
            if(IsInvalid(L)) break;
            LinkPrint(L);
            cout<<endl;
            break;
        case 11:
            cout<<"请输入要插入链表的元素个数:";
            cin>>s;
            CreateList_R(L,s);
            break;
        case 12:
            return 0;
            break;
        case 13:
            if(IsInvalid(L)) break;
            if(IsEmpty(L))
                cout<<"链表为空!"<<endl;
            else
                cout<<"非空!"<<endl;
            break;
        case 14:
            if(IsInvalid(L)) break;
            if(ReverseList(L))
                cout<<"链表逆转成功!"<<endl;
            else
                cout<<"操作失败!"<<endl;
            break;
        default:
            cout<<"操作有误!"<<endl;
        }
        cout<<"请输入你的选择:";
    }
    return 0;
}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值