单链表的定义及基本操作
顺序表的定义及基本操作和单链表的定义及基本操作
数据结构实验报告壹题目一:顺序表的定义及基本操作题目二:单链表的定义及基本操作班级:信息一班姓名:学号:得分:____ (满分2.5分)线性表#include<iostream.h>#define OVERFLOW -2#define OK 1#define ERROR 0#define LIST_INIT_SIZE 100#define LISTINCREMENT 10typedef int ElemType;typedef int status;typedef struct{ElemType *elem;int length;int listsize;}sqlist;status lnitlist_sq(sqlist &L){L.elem=new ElemType[LIST_INIT_SIZE];if(!L.elem)cout<<OVERFLOW;L.length=0;L.listsize=LIST_INIT_SIZE;return OK;}int LocateElem(sqlist L, ElemType e){int *p ;p=L.elem; int i=1;while(i<=L.length && *p++!=e) i++;return i<=L.length ? i : 0;}status GetElem(sqlist L, int i, ElemType &e) {if(i<1||i>L.length) return ERROR; //i非法e=*(L.elem + i - 1);return OK;}status ListInsert(sqlist &L, int i, ElemType e) {//前插操作int *newbase,*q,*p;if(i<1||i>L.length+1) return ERROR; // i非法if(L.length>=L.listsize){ //需要扩展数组newbase=new ElemType[L.listsize+LISTINCREMENT];if(!newbase)cout<<OVERFLOW;L.elem=newbase;L.listsize+=LISTINCREMENT;} //end ifq=L.elem+i-1; //令q指向aifor( p=L.elem+L.length-1; p>=q; p--)*(p+1)=*p; //右移一位*q=e; //将e放入第i个元素的位置上++L.length;return OK;} //ListInsertstatus ListDelete(sqlist &L, int i, ElemType &e){//删除顺序表的第i 个元素,用e返回被删元素的值int *p;if(i<1||i>L.length) return ERROR; //i非法p=&(L.elem[i-1]); //令指针p指向aie=*p;for(++p; p<=L.elem+L.length-1; ++p)*(p-1)=*p; //ai+1…an左移一位--L.length ; //表的长度减1return e;} //ListDeletestatus DestroyList(sqlist &L){delete []L.elem;return OK;}void ListTraverse(sqlist L){if(L.length){for(int i=0;i<L.length;i++){cout<<L.elem[i]<<"\t";}}else cout<<"此顺序表为空!"<<endl;}void main(){int m,n;sqlist a;lnitlist_sq(a);cout<<"线性表初始长度:"<<a.length<<endl;cout<<"请输入线性表的10个元素:"<<endl;for(int i=0;i<10;i++,a.length++)cin>>a.elem[i] ;cout<<"线性表当前长度:"<<a.length<<endl;cout<<"调用遍历函数"<<endl; ListTraverse(a );cout<<"调用定位函数"<<endl;cout<<LocateElem(a,9)<<endl;cout<<"调用读表元函数"<<endl;cout<<GetElem(a, 5, m)<<endl;cout<<"在第五个元素前插入8"<<endl;cout<<ListInsert(a, 5, 8)<<endl;ListTraverse(a );cout<<endl;cout<<"删除第五个元素并返回"<<endl;cout<<ListDelete(a, 5, n)<<endl;ListTraverse(a );cout<<endl;cout<<"销毁线性表"<<DestroyList(a)<<endl;}单链表#include<iostream.h>#define OVERFLOW -2#define OK 1#define ERROR 0#define LIST_INIT_SIZE 10typedef int status;typedef struct LNode {int data ;struct LNode *next ;} LNode, *LinkList;status InitList ( LinkList &L ){//L是带头结点的单链表的头指针L=new LNode[LIST_INIT_SIZE]; //申请头结点if(!L)cout<<OVERFLOW;L->next=NULL;return OK;}status GetElem (LinkList L, int i, int &e){//L是带头结点的单链表,读L的第i个元素,用e返回其值LNode *p;int j;p=L->next; j=1; //指针p指向a1while(p && j<i){p=p->next; j++;} //指针p右移i-1次if(!p||j>i)return ERROR; //i非法!p--i太大,j>i--i太小e=p->data;return e;} //GetElemstatus ListLength ( LinkList L ){// L是带头结点的单链表int n;LNode *p;p=L->next; n=0;while(p) {n++; p=p->next;}cout<<n;return OK;} //ListLength O(n)status ListInsert( LinkList &L, int i, int e ){// L是带头结点的单链表,在ai之前插入新结点eLNode *s;LNode *p;int j;p=L; j=0; //p指向头结点,j是计数器while(p && j<i-1){ p=p->next; j++; } //令p指向ai-1if (!p || j>i-1) return ERROR; //i非法s=new LNode[LIST_INIT_SIZE+2];s->data=e;s->next=p->next; p->next=s; //修改指针return OK;} // ListInsertstatus ListDelete( LinkList &L, int i, int &e ){// L是带头结点的单链表,删除ai,用参数e返回被删结点的值LNode *q,*p;int j;p=L; j=0; //p指向头结点,j是计数器while(p && j<i-1){p=p->next; j++;} //p指向ai-1 if (!(p->next) || j>i-1) return ERROR; // i非法q=p->next; e=q->data;p->next=q->next; delete(q); //修改指针return OK;} // ListInsert O(n)int LocateElem(LinkList L, int e){LNode *p;p=L->next ;int i=1;while(i && p->data!=e){ i++;*p++;}return i;}void main(){int m,n ;LinkList a;LNode s1, s2, s3, s4, s5;InitList (a );a->next=&s1 ;s1.next=&s2 ;s2.next=&s3;s3.next=&s4;s4.next=&s5;cout<<"请输入5个元素:"<<endl;cin>>s1.data>>s2.data>>s3.data>>s4.data>>s5.data; cout<<"执行读表元操作"<<endl;cout<<GetElem (a, 3, m)<<endl;cout<<"执行插入操作"<<endl;cout<<ListInsert(a, 3, 8 ) <<endl;cout<<"执行删除操作"<<endl;cout<<ListDelete( a, 3, n )<<endl;cout<<"执行定位操作"<<endl;cout<<LocateElem( a, 3)<<endl;}。
数据结构实验报告--单链表
数据结构实验报告--单链表数据结构实验报告--单链表1.引言1.1 研究目的本实验旨在通过实践的方式,深入了解单链表的数据结构以及相关操作,提升对数据结构的理解和应用能力。
1.2 实验内容本实验主要包括以下几个方面的内容:●单链表的基本定义和实现●单链表的插入、删除、遍历操作●单链表的逆置操作●单链表的查找和修改操作2.理论基础2.1 单链表的定义单链表是一种常见的线性数据结构,它由一系列的节点组成,每个节点包含数据和指向下一个节点的指针。
2.2 单链表的基本操作①单链表的插入操作在单链表中,可以通过插入操作在指定位置插入一个新节点,该操作主要包括以下步骤:●创建一个新的节点,并为其赋值●将新节点的next指针指向插入位置的后一个节点●将插入位置的前一个节点的next指针指向新节点②单链表的删除操作在单链表中,可以通过删除操作删除指定位置的节点,该操作主要包括以下步骤:●将删除位置的前一个节点的next指针指向删除位置的后一个节点●释放删除节点的内存③单链表的遍历操作单链表的遍历操作主要是依次访问链表中的每一个节点,并执行相应的操作。
④单链表的逆置操作单链表的逆置操作可以将一个单链表中的节点顺序进行颠倒。
⑤单链表的查找操作在单链表中,可以通过查找操作找到指定值的节点。
⑥单链表的修改操作在单链表中,可以通过修改操作修改指定位置的节点的值。
3.实验过程3.1 实验环境本次实验使用C语言进行编程,需要先安装相应的编程环境,如gcc编译器。
3.2 实验步骤①单链表的创建和初始化首先创建一个空链表,并初始化链表的头指针。
②单链表的插入操作按照需求,在链表的指定位置插入一个新节点。
③单链表的删除操作按照需求,删除链表中的指定位置的节点。
④单链表的遍历操作依次访问链表中的每一个节点,并输出其值。
⑤单链表的逆置操作将单链表中的节点顺序进行逆置。
⑥单链表的查找操作按照需求,在链表中查找指定值的节点。
3.2.7 单链表的修改操作按照需求,修改链表中指定位置的节点的值。
单链表基本操作的实现
单链表基本操作的实现单链表是一种常见的数据结构,它由多个节点组合而成,每个节点包含一个数据元素和一个指向下一个节点的指针。
通过指针,我们可以方便地在单链表中进行插入、删除和遍历等操作。
以下是关于单链表基本操作的实现。
1. 单链表的创建单链表的创建需要定义一个空的头结点,它的作用是方便在链表的头部进行添加和删除节点操作。
一个空的头节点可以在链表初始化的过程中进行创建。
```typedef struct Node{int data;struct Node *next;}Node;Node *createList(){Node *head = (Node*)malloc(sizeof(Node)); //创建空的头节点head->next = NULL;return head; //返回头节点的地址}```2. 单链表的插入单链表的插入可以分为在链表头部插入、在链表尾部插入和在链表中间插入三种情况。
a. 在链表头部插入节点:```void insertAtHead(Node *head, int data){Node *node = (Node*)malloc(sizeof(Node));node->data = data;node->next = head->next;head->next = node;}```b. 在链表尾部插入节点:```void insertAtTail(Node *head, int data){Node *node = (Node*)malloc(sizeof(Node));node->data = data;node->next = NULL;Node *p = head;while(p->next != NULL){p = p->next;}p->next = node;}```c. 在链表中间插入节点:```void insertAtMid(Node *head, int data, int pos){ Node *node = (Node*)malloc(sizeof(Node)); node->data = data;node->next = NULL;Node *p = head;int count = 0;while(p->next != NULL && count < pos-1){ p = p->next;count++;}if(count == pos-1){node->next = p->next;p->next = node;}else{printf("插入位置错误!");}}```3. 单链表的删除单链表的删除可以分为在链表头部删除、在链表尾部删除和在链表中间删除三种情况。
单链表数据结构
插入
if (p != NULL && j == i-1) { // 找到第i个结点
s = (LinkList) malloc ( sizeof (LNode)); // 生成新结点
s->data = e;
// 数据域赋值
s->next = p->next; //新结点指针指向后一结点
p->next = s; return OK;
6、销毁
4.6 销毁操作
while(L) { p = L->next; free(L); L=p;
// p指向第一结点(头节点为“哑结点”) // 释放首结点 // L指向p
}
// 销毁完成后,L为空(NULL)
算法的时间复杂度为:O(ListLength(L))
判空 求表长
4.7 其它操作
if(L->next==NULL) return TRUE; // 空
5、清空
4.5 清空操作
while (L->next) { p = L->next; L->next = p->next; free(p);
// p指向当前结点 // 头结点指向当前结点的后结点 // 释放当前结点内存
}
// 清空完成后,仍保留头结点L
算法的时间复杂度为:O(ListLength(L))
点。
5.1.2 逆序建立单链表
①建立一个带头结点的空单链表;
②输入数据元素ai,建立新结点p, 并把p插入在头结点之后成为第一个 结点。
③重复执行②步,直到完成单链表的 建立。
a1
a2 a1
创建出来的链表 点顺序与插入操作
顺序相反。
单链表存储结构的概念
单链表存储结构的概念
单链表是一种常见的线性存储结构,用于存储一系列元素。
它由一系列节点(Node)组成,每个节点包含两部分:数据域和指针域。
1.数据域(Data域):数据域用于存储节点所携带的信息,可以是任意类型的数据,例如整数、字符、对象等。
2.指针域(Next指针):指针域用于指向下一个节点的位置。
通过指针,单链表将各个节点按顺序连接起来,形成链式结构。
链表的最后一个节点的指针域通常指向空值(null),表示链表的结束。
单链表的基本特点包括:
-动态性:单链表的长度可以动态变化,可以方便地进行插入和删除操作,而不需要提前分配存储空间。
-非连续性:单链表中的节点在内存中可以是分散的,它们通过指针相互连接,不像数组那样需要一块连续的存储空间。
-随机访问困难:由于单链表是非连续的,因此访问某个特定位置的元素时需要从头节点开始依次遍历,效率较低。
单链表的操作包括:
-插入(Insert):在链表的特定位置或链尾插入一个新的节点。
-删除(Delete):删除链表中的某个节点。
-查找(Search):查找链表中是否存在某个特定值的节点。
-遍历(Traverse):依次访问链表中的每个节点。
单链表是一种常见的数据结构,常被用于需要频繁插入和删除操作的场景。
数据结构课件单链表
删除链表中的节点需要遍历至指定位置,时间复杂度为 O(n)。
查找节点
在链表中查找一个节点需要遍历整个链表,时间复杂度为 O(n)。
空间复杂度
空间占用
单链表的空间占用主要取决于链表中的 节点数,因此空间复杂度为O(n)。
VS
内存分配
每个节点需要分配内存空间存储数据和指 针,因此内存分配的空间复杂度也为O(n) 。
需要根据数据元素顺 序进行遍历的场景, 如排序算法等。
需要频繁插入、删除 操作的场景,如动态 规划、图算法等。
02
单链表的实现
创建单链表
定义节点结构体
首先需要定义一个节点结构体,包含 数据域和指针域两个部分,数据域用 于存储数据,指针域用于指向下一个 节点。
初始化头节点
创建一个头节点,并将其指针域指向 NULL,表示单链表的起始位置。
05
单链表常见问题与解决方 案
循环链表
总结词
循环链表是一种特殊类型的单链表,其中尾节点的指针指向头节点,形成一个闭环。
详细描述
在循环链表中,由于尾节点的指针指向头节点,因此遍历链表时需要特别注意,以避免无限循环。常见的解决方 法是在遍历时记录已经访问过的节点,避免重复访问。
链表中的重复元素
总结词
链表中可能存在重复元素的问题,这会影响数据处理的正确性。
详细描述
为了解决这个问题,可以在插入节点时检查新元素是否已存在于链表中。如果存在,则不进行插入操 作。另外,也可以使用哈希表等数据结构来快速查找重复元素。
链表的排序
总结词
对链表进行排序是常见的需求,但链表的排 序算法通常比数组的排序算法复杂。
合并单链表
总结词
将两个已排序的单链表合并为一个新的已排序的单链表。
单链表的基本操作
实验二:单链表的基本操作编写一个完整的程序,实现单链表的建立、插入、删除、输出等基本操作。
(1)建立一个带头结点的单链表。
(2)计算单链表的长度,然后输出单链表。
(3)查找值为x的直接前驱结点q。
(4)删除值为x的结点。
(5)把单向链表中元素逆置(不允许申请新的结点空间)。
(6)已知单链表中元素递增有序,请写出一个高效的算法,删除表中所有值大于mink且小于maxk的元素(若表中存在这样的元素),同时释放被删结点空间,并分析你的算法的时间复杂度(注意:mink和maxk是给定的两个参变量,他们的值可以和表中的元素相同,也可以不同)。
(7)同(6)的条件,试写一高效的算法,删除表中所有值相同的多余元素(使得操作后的线性表中所有元素的值均不相同),同时释放被删结点空间,并分析你的算法时间复杂度。
(8)利用(1)建立的链表,实现将其分解成两个链表,其中一个全部为奇数,另一个全部为偶数(尽量利用已知的存储空间)。
(9)在主函数中设计一个简单的菜单,分别测试上述算法。
# include <stdio.h># include <stdlib.h>typedef struct node{int data;struct node * next;}Lnode, * LinkList;int m=sizeof(Lnode);//建立新的链表void Bulid_List(LinkList root){int num;LinkList s,p;s=root->next;int n;printf("请输入新建链表的长度n数据:\n"); scanf("%d",&n);printf("请依次建立链表:");for(int i=0;i<n;i++){scanf("%d",&num);s->data=num;p=(LinkList)malloc(m);s->next=p;s=p;s->next=NULL;}printf("链表已建立!\n");}//对链表的输出,包括长度和元素void OutPut_list(LinkList root) {int len=0;LinkList s;s=root->next;if(s->next==NULL)printf("单链表无数据,请先新建单链表。
pta 单链表基本操作
pta 单链表基本操作
单链表是一种常见的数据结构,由一个个节点组成,每个节点包含一个数据元素和一个指向下一个节点的指针。
基本操作包括以下几种:
1. 创建链表:创建一个空链表,即创建一个头节点。
2. 插入节点:在链表的任意位置插入一个节点。
- 头部插入:将新节点作为新的头节点,其指针指向原头节点。
- 中间插入:将新节点插入到指定位置的节点之前,其指针指向指定位置的节点。
- 尾部插入:找到链表尾部节点,将新节点插到尾部节点的后面。
3. 删除节点:在链表中删除指定节点。
- 头部删除:将头节点删除,将头节点的下一个节点作为新的头节点。
- 中间删除:找到指定节点的前驱节点,将前驱节点的指针指向指定节点的后继节点。
- 尾部删除:找到尾部节点的前驱节点,将前驱节点的指针设为NULL。
4. 查找节点:在链表中查找指定数据的节点。
- 遍历链表,逐个比较节点的数据元素,直到找到指定数据或遍历到末尾节点。
5. 修改节点:在链表中修改指定节点的数据。
- 遍历链表,找到指定节点,修改其数据元素。
6. 遍历链表:按顺序遍历链表中的所有节点,进行相应操作。
这些是单链表的基本操作,可以根据需求进行组合和扩展。
实验二 单链表基本操作
实验二单链表基本操作一实验目的1.学会定义单链表的结点类型,实现对单链表的一些基本操作和具体的函数定义,了解并掌握单链表的类定义以及成员函数的定义与调用。
2.掌握单链表基本操作及两个有序表归并、单链表逆置等操作的实现。
二实验要求1.预习C语言中结构体的定义与基本操作方法。
2.对单链表的每个基本操作用单独的函数实现。
3.编写完整程序完成下面的实验内容并上机运行。
4.整理并上交实验报告。
三实验内容1.编写程序完成单链表的下列基本操作:(1)初始化单链表La。
(2)在La中第i个元素之前插入一个新结点。
(3)删除La中的第i个元素结点。
(4)在La中查找某结点并返回其位置。
(5)打印输出La中的结点元素值。
2 .构造两个带有表头结点的有序单链表La、Lb,编写程序实现将La、Lb合并成一个有序单链表Lc。
合并思想是:程序需要3个指针:pa、pb、pc,其中pa,pb分别指向La表与Lb表中当前待比较插入的结点,pc 指向Lc表中当前最后一个结点。
依次扫描La和Lb中的元素,比较当前元素的值,将较小者链接到*pc 之后,如此重复直到La或Lb结束为止,再将另一个链表余下的内容链接到pc所指的结点之后。
3.构造一个单链表L,其头结点指针为head,编写程序实现将L逆置。
(即最后一个结点变成第一个结点,原来倒数第二个结点变成第二个结点,如此等等。
)四思考与提高1.如果上面实验内容2中合并的表内不允许有重复的数据该如何操作?2.如何将一个带头结点的单链表La分解成两个同样结构的单链表Lb,Lc,使得Lb中只含La表中奇数结点,Lc中含有La表的偶数结点?1.编写程序完成单链表的下列基本操作:(1)初始化单链表La。
(2)在La中第i个元素之前插入一个新结点。
(3)删除La中的第i个元素结点。
(4)在La中查找某结点并返回其位置。
(5)打印输出La中的结点元素值。
#include<stdio.h>#include<stdlib.h>#include <malloc.h>#define OK 1#define ERROR 0typedef int Status;typedef int ElemType;//定义存储结构typedef struct Lnode{int data; /*每个元素数据信息*/struct Lnode *next; /*存放后继元素的地址*/} LNode,*LinkList;int main(){void Create_L(LinkList &L,int n);void Print_L(LinkList L);Status ListInsert_L(LinkList &L,int i,ElemType e);Status ListDelete_L(LinkList &L,int i,ElemType &e);Status Find_L(LinkList L,int e);LinkList La;//创建单链表Laint n;printf("请输入链表La中的元素个数:\n");scanf("%d",&n);Create_L(La,n);//初始化单链表printf("现在La中的元素为:\n");Print_L(La);printf("-------------------------------------\n\n");printf("现在准备插入元素,请输入插入位置及所插入元素的值\n");int i,e;scanf("%d %d",&i,&e);ListInsert_L(La,i,e);printf("插入后La中的元素为:\n");Print_L(La);printf("-------------------------------------\n\n");printf("现在准备删除元素,请输入删除位置\n");scanf("%d",&i);ListDelete_L(La,i,e);printf("删除后La中的元素为:\n");Print_L(La);printf("-------------------------------------\n\n");printf("请输入所要查找元素的值:\n");scanf("%d",&e);Find_L(La,e);printf("所要查找元素的位置为:%d\n",Find_L(La,e)); }void Create_L(LinkList &L,int n){int j=1;L=(LinkList)malloc(sizeof(Lnode));L->next =NULL;//先建立一个带头结点的单链线性表L for(int i=n;i>0;--i){LinkList p=(LinkList)malloc(sizeof(Lnode));printf("请输入链表La中的第%d个元素:\n",j++);scanf("%d",&p->data);p->next=L->next;L->next =p;}//(逆序实现)/*LinkList q=L;for(int i=1;i<=n;i++){LinkList p=(LinkList)malloc (sizeof(Lnode));q->next=p;p->next=NULL;q=q->next ;printf("请输入链表La中的第%d个元素:\n",i);scanf("%d",&p->data);}//(正序实现)*/}//初始化单链表//输出单链表void Print_L(LinkList L){LinkList p;p=L->next;while(p){printf("%d ",p->data );p=p->next;}printf("\n");}//在单链表L的第i个位置前插入元素eStatus ListInsert_L(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 ERROR;LinkList s=(LinkList)malloc(sizeof(LNode));s->data=e; s->next=p->next;p->next=s;return OK;} //ListInsert_L//删除单链表L中第i个位置上的元素Status ListDelete_L(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 ERROR;LinkList q=p->next; p->next=q->next;e=q->data;free(q);return OK;}//LinkDelete_L/*查找元素并返回位置*/Status Find_L(LinkList L,int e){LinkList p=L->next;int j=1;while(p->data!=e&&p->next){p=p->next;j++;}if(p->data==e) return j;else{printf("无当前元素\n");return ERROR;}if(!p){printf("无当前元素\n");return ERROR;}}//定位2 .构造两个带有表头结点的有序单链表La、Lb,编写程序实现将La、Lb合并成一个有序单链表Lc。
c语言单链表尾插法
c语言单链表尾插法摘要:一、单链表的概念1.单链表的定义2.单链表的特点二、尾插法的原理1.尾插法的定义2.尾插法的基本思想三、C 语言实现尾插法1.创建链表节点结构体2.定义尾插法函数3.插入节点操作四、尾插法的优缺点1.优点2.缺点五、总结正文:一、单链表的概念单链表是一种线性数据结构,它由若干个节点组成,每个节点只包含一个指向下一个节点的指针。
单链表的特点是插入和删除操作方便,但查找操作较慢。
二、尾插法的原理尾插法是一种在单链表尾部插入节点的算法。
它的基本思想是:当需要插入一个新节点时,遍历链表,找到尾节点,然后将新节点的指针指向尾节点的下一个节点,最后将尾节点的指针指向新节点。
三、C 语言实现尾插法1.创建链表节点结构体```ctypedef struct Node {int data;struct Node* next;} Node;```2.定义尾插法函数```cvoid append(Node** head, int data) {Node* newNode = (Node*)malloc(sizeof(Node));newNode->data = data;newNode->next = NULL;if (*head == NULL) {*head = newNode;} else {Node* temp = *head;while (temp->next != NULL) {temp = temp->next;}temp->next = newNode;}}```3.插入节点操作```cint main() {Node* head = NULL;append(&head, 1);append(&head, 2);append(&head, 3);Node* temp = head;while (temp != NULL) {printf("%d -> ", temp->data);temp = temp->next;}printf("NULL");return 0;}```四、尾插法的优缺点1.优点:尾插法在插入节点时,只需操作尾节点,无需遍历整个链表,因此时间复杂度较低,适合频繁插入的场景。
单链表的操作实验报告
单链表的操作实验报告《单链表的操作实验报告》在计算机科学领域,数据结构是非常重要的基础知识之一。
而单链表作为一种常见的数据结构,经常被用来存储和操作数据。
在本次实验中,我们将对单链表的操作进行实验,并撰写实验报告以总结和分享我们的实验结果。
实验目的:1. 了解单链表的基本概念和操作方法。
2. 掌握单链表的插入、删除、查找等操作。
3. 通过实际操作加深对单链表的理解和掌握。
实验环境:1. 编程语言:C/C++2. 开发环境:Visual Studio Code3. 实验工具:GCC编译器实验步骤:1. 定义单链表的结构体,并实现初始化、插入、删除、查找等操作的函数。
2. 编写测试用例,对单链表的各种操作进行测试。
3. 分析实验结果,总结操作的时间复杂度和空间复杂度。
4. 撰写实验报告,分享实验过程和结果。
实验结果:经过实验,我们成功实现了单链表的初始化、插入、删除、查找等操作,并对这些操作进行了充分的测试。
我们发现单链表的插入和删除操作的时间复杂度为O(1),而查找操作的时间复杂度为O(n),其中n为链表的长度。
这些结果与我们的预期相符合,说明我们对单链表的操作有了较好的掌握。
实验总结:通过本次实验,我们不仅加深了对单链表的理解,还提高了编程能力和数据结构的应用能力。
我们对单链表的操作有了更深入的了解,为以后在实际项目中应用单链表打下了良好的基础。
结语:单链表作为一种常见的数据结构,在实际应用中具有重要的作用。
通过本次实验,我们对单链表的操作有了更深入的了解,相信在以后的学习和工作中能够更好地应用和运用单链表。
希望本次实验报告能够对读者有所帮助,也欢迎大家对实验结果进行讨论和交流。
数据结构实验报告单链表
数据结构实验报告_单链表数据结构实验报告——单链表一、实验目的1.掌握单链表的基本概念和原理。
2.了解单链表在计算机科学中的应用。
3.掌握单链表的基本操作,如插入、删除、遍历等。
4.通过实验,加深对理论知识的理解,提高编程能力。
二、实验内容1.实验原理:单链表是一种线性数据结构,由一系列节点组成,每个节点包含数据域和指针域。
其中,指针域指向下一个节点,最后一个节点的指针域指向空。
单链表的主要操作包括插入、删除、遍历等。
2.实验步骤:(1)创建一个单链表。
(2)实现插入操作,即在链表的末尾插入一个新节点。
(3)实现删除操作,即删除链表中的一个指定节点。
(4)实现遍历操作,即输出链表中所有节点的数据。
3.实验代码:下面是使用Python语言实现的单链表及其基本操作的示例代码。
class Node:def __init__(self, data):self.data = dataself.next = Noneclass LinkedList:def __init__(self):self.head = Nonedef insert(self, data):new_node = Node(data)if self.head is None:self.head = new_nodeelse:current = self.headwhile current.next is not None:current = current.nextcurrent.next = new_nodedef delete(self, data):if self.head is None:returnif self.head.data == data:self.head = self.head.nextreturncurrent = self.headwhile current.next is not None and current.next.data != data:current = current.nextif current.next is None:returncurrent.next = current.next.nextdef traverse(self):current = self.headwhile current is not None:print(current.data)current = current.next4.实验结果:通过运行上述代码,我们可以看到单链表的基本操作得到了实现。
实验二 单链表的插入和删除
实验二 单链表的插入和删除1.实验目的:了解单链表的基本概念、结构的定义及在单链表上的基本操作(插入、删除、查找以及线性表合并),通过在VC 实现以上操作更好的了解书本上的内容并体会线性表的两种存储结构的区别。
2.实验预备知识:⑴ 复习C 语言中指针的用法,特别是结构体的指针的用法;⑵ 了解单链表的概念,单链表的定义方法;单链表是线性表的链式存储表示,是用一组任意的存储单元依次存储线性表的数据元素。
因此,为了表示每个数据元素a i 与其直接后继元素a i+1之间的逻辑关系,对数据元素ai 来说,,除了存储其本身的信息之外,还需存储一个指示其直接后继的信息(即直接后继的存储位置),而这部分就是用指针来完成的。
⑶ 掌握线性表在链式存储结构上实现基本操作:查找、插入、删除的算法; 在实现这些算法的时候,要注意判断输入数据的合法性,除此之外还要要注意以下内容:在实现查找的时候,首先要判断该顺序表是否为空,其次要判断查找后的结果(查到时输出查到的数据,未查到时给出错误提示)。
在实现插入的时候,由于是链式存储,它可以随机产生和回收存储空间,所以它不要判断线性表是否为满,但仍需判断要插入的位置是否合法,原因同实验一,其次要注意插入的时候语句的顺序不可颠倒,否则出错。
例如:s 所指向结点要插入在p 所指向的结点之后,则:正确形式:s->next=p->nextp->next=s错误形式:p->next=ss->next=p->next(因为此时p->next 已经指向s 了)在实现删除的时候,首先要判断线性表是否为空,为空则不能删除; 其次在删除后要回收空间。
例如:删除如上图所示s 所指向的结点p->next=p->next->nextfree s3.实验内容:⑴ 单链表的插入算法⑵ 单链表的删除算法⑶循环链表的插入和删除算法4.部分实验代码:⑴单链表的结构定义:#include <stdio.h>typedef int elemtype;typedef struct lnode{ elemtype data;struct lnode *next;}*linklist;⑵建立单链表的算法int n; /*n作为整个程序的全局变量*/linklist *creat(void){ linklist *head, *p1, *p2;n=0;p1=p2=(linklist *)malloc(sizeof(linklist));scanf(“%d”,&p1->data);head=null;while(p1->data!=0){ n=n+1;if(n==1) head=p1;else p2->next=p1;p2=p1;p1=(linklist *)malloc(sizeof(linklist));scanf(“%d”,&p1->data);}p2->next=null;return(head);}⑶单链表的插入算法int insert(linklist *head, int i,elemtype e) { linklist *p, *s;int j;p=head; j=0;while(p && j<i-1){ p=p->next;++j;}if(!p||j>i-1){ printf(“无法插入”);return 0;}s=(linklist *)malloc(sizeof(lnode));s->data=e;s->next=p->next;p->next=s;return 1;}⑷单链表的删除算法int deltree(linklist *head,int i,elemtype e){ linklist *p, *q;int j;lp=head; j=0;while(p->next && j<i-1){ p=p->next;++j;}if(!(p->next)||j>i-1){ printf(“无法删除”);return 0;}q=p->next;p->next=q->next;e=q->data;free(q);return 1;}。
单链表的基本操作代码
单链表的基本操作代码单链表是一种常用的数据结构,它具有优秀的插入和删除性能,在数据存储和处理方面具有广泛的应用。
单链表的基本操作包含创建链表、插入节点、删除节点、查找节点等,下面是单链表的基本操作代码:1. 定义单链表结构体:typedef struct ListNode {int val;struct ListNode *next;} ListNode;2. 创建单链表:ListNode *createList(int arr[], int n) {ListNode *head = NULL, *tail = NULL, *p = NULL;for(int i = 0; i < n; i++) {p = (ListNode *)malloc(sizeof(ListNode));p->val = arr[i];p->next = NULL;if(head == NULL) {head = tail = p;} else {tail->next = p;tail = p;}}return head;}3. 插入节点:void insertNode(ListNode **head, int val, int pos) {ListNode *p = (ListNode *)malloc(sizeof(ListNode)); p->val = val;p->next = NULL;if(*head == NULL) {if(pos != 0) {printf("Invalid position\n");return;} else {*head = p;return;}}if(pos == 0) {p->next = *head;*head = p;} else {int i = 0;ListNode *q = *head;while(q != NULL && i < pos - 1) {q = q->next;i++;}if(q == NULL || i != pos - 1) {printf("Invalid position\n");return;}p->next = q->next;q->next = p;}}4. 删除节点:void deleteNode(ListNode **head, int pos) {if(*head == NULL) {printf("List is empty\n");return;}if(pos == 0) {ListNode *p = *head;*head = (*head)->next;free(p);} else {int i = 0;ListNode *p = *head, *q = NULL; while(p != NULL && i < pos) { q = p;p = p->next;i++;}if(p == NULL || i != pos) {printf("Invalid position\n");return;}q->next = p->next;free(p);}}5. 查找节点:ListNode *findNode(ListNode *head, int val) {ListNode *p = head;while(p != NULL) {if(p->val == val) {return p;}p = p->next;}return NULL;}单链表的基本操作是数据结构中最基础的部分,掌握好这些代码对于往后的学习和应用都会有很大的帮助。
数据结构 实验二:单链表的基本操作
数据结构实验二:单链表的基本操作数据结构实验二:单链表的基本操作实验二:单链表的基本操作一、【实验目的】1、理解和掌握单链表的类型定义方法和结点生成方法。
2、掌握建立单链表和显示单链表元素的算法。
3、掌握单链表的查找、插入和删除算法二、【实验内容】1、建立一个整形数的单链表,手动输入10个数,并从屏幕显示单链表元素列表。
2、从键盘输入一个数,查找在以上创建的单链表中是否存在该数;如果存在,显示它的位置;如果不存在,给出相应提示。
3、删除上述单链表中指定位置的元素。
以下就是程序部分代码,恳请调试并补足并使之恰当运转:1.linlist.htypedefstructnode{datatypedata;structnode*next;}slnode;voidlistinitiate(slnode**head)/*初始化*/{/*如果有内存空间,申请头结点空间并使头指针head指向头结点*/if((*head=(slnode*)malloc(sizeof(slnode)))==null)exit(1);(*head)->next=null;/*置链尾标记null*/}intlistlength(slnode*head){slnode*p=head;/*p指向首元结点*/intsize=0;/*size初始为0*/while(p->next!=null)/*循环计数*/{p=p->next;size++;}returnsize;}intlistinsert(slnode*head,inti,datatypex)/*在带头结点的单链表head的数据元素ai(0≤i≤size)结点前*//*填入一个存放数据元素x的结点*/{slnode*p,*q;intj;p=head;/*p指向首元结点*/j=-1;/*j起始为-1*/while(p->next!=null&&j<i-1)/*最终让指针p指向数据元素ai-1结点*/{p=p->next;j++;}if(j!=i-1){printf(\填入边线参数弄错!\return0;}/*生成新结点由指针q指示*/if((q=(slnode*)malloc(sizeof(slnode)))==null)exit(1);q->data=x;q->next=p->next;/*给指针q->next赋值*/p->next=q;/*给指针p->next重新赋值*/return1;}intlistdelete(slnode*head,inti,datatype*x)/*删除带头结点的单链表head的数据元素ai(0≤i≤size-1)结点*//*删除结点的数据元素域值由x带回。
数据结构单链表实验报告
数据结构单链表实验报告实验目的:本实验的目的是通过实现单链表数据结构,加深对数据结构的理解,并掌握单链表的基本操作和算法。
实验内容:1、单链表的定义单链表由若干个节点组成,每个节点包含数据域和指针域,数据域存储具体数据,指针域指向下一个节点。
单链表的头指针指向链表的第一个节点。
2、单链表的基本操作2.1 初始化链表初始化链表时,将头指针置空,表示链表为空。
2.2 插入节点插入节点可以分为头插法和尾插法。
- 头插法:将新节点插入链表头部,新节点的指针域指向原头节点,头指针指向新节点。
- 尾插法:将新节点插入链表尾部,新节点的指针域置空,原尾节点的指针域指向新节点。
2.3 删除节点删除节点可以分为按位置删除和按值删除两种方式。
- 按位置删除:给定要删除节点的位置,修改前一节点的指针域即可。
- 按值删除:给定要删除节点的值,遍历链表找到对应节点,修改前一节点的指针域即可。
2.4 遍历链表遍历链表即按顺序访问链表的每个节点,并输出节点的数据。
2.5 查找节点查找节点可以分为按位置查找和按值查找两种方式。
- 按位置查找:给定节点的位置,通过遍历链表找到对应节点。
- 按值查找:给定节点的值,通过遍历链表找到第一个匹配的节点。
实验步骤:1、根据实验目的,定义单链表的结构体和基本操作函数。
2、实现初始化链表的函数,将头指针置空。
3、实现头插法或尾插法插入节点的函数。
4、实现按位置删除节点的函数。
5、实现按值删除节点的函数。
6、实现遍历链表的函数,输出节点的数据。
7、实现按位置查找节点的函数。
8、实现按值查找节点的函数。
9、设计实验样例,测试单链表的各种操作。
实验结果与分析:通过测试实验样例,我们可以验证单链表的各种操作是否正确。
如果出现异常情况,可通过调试找出问题所在,并进行修改。
单链表的操作时间复杂度与操作的位置有关,对于查找操作,时间复杂度为O(n);对于插入和删除操作,时间复杂度也为O(n)。
附件:1、单链表的定义和基本操作的源代码文件。
数据结构单链表实验报告
数据结构单链表实验报告一、实验目的本次实验旨在深入理解和掌握数据结构中单链表的基本概念、操作原理及实现方法。
通过实际编程实现单链表的创建、插入、删除、查找等基本操作,提高对数据结构的理解和编程能力。
二、实验环境本次实验使用的编程环境为具体编程语言,编译工具为具体编译工具名称。
三、实验原理1、单链表的定义单链表是一种线性表的数据结构,它由一系列节点组成,每个节点包含数据域和指针域。
数据域用于存储节点的数据,指针域用于指向下一个节点的地址。
通过这种方式,将各个节点连接起来,形成一个链表。
2、单链表的基本操作创建单链表:从无到有构建一个单链表,可以通过逐个插入节点来实现。
插入节点:可以在链表的头部、尾部或指定位置插入新的节点。
删除节点:根据给定的条件或位置删除链表中的节点。
查找节点:在链表中查找满足特定条件的节点。
四、实验内容1、单链表节点的定义```具体编程语言typedef struct Node {int data;struct Node next;} Node;```2、创建单链表```具体编程语言Node createList(){Node head = NULL;Node newNode;int data;printf("请输入节点数据(输入-1 结束):");scanf("%d",&data);while (data!=-1) {newNode =(Node )malloc(sizeof(Node));newNode>data = data;newNode>next = NULL;if (head == NULL) {head = newNode;} else {Node temp = head;while (temp>next!= NULL) {temp = temp>next;}temp>next = newNode;}printf("请输入节点数据(输入-1 结束):");scanf("%d",&data);}return head;}```3、插入节点在头部插入```具体编程语言Node insertAtHead(Node head, int data) {Node newNode =(Node )malloc(sizeof(Node));newNode>data = data;newNode>next = head;head = newNode;return head;}```在尾部插入```具体编程语言void insertAtTail(Node head, int data) {Node newNode =(Node )malloc(sizeof(Node));newNode>data = data;newNode>next = NULL;Node temp = head;while (temp>next!= NULL) {temp = temp>next;}temp>next = newNode;}```在指定位置插入```具体编程语言void insertAtPosition(Node head, int position, int data) {Node newNode =(Node )malloc(sizeof(Node));newNode>data = data;if (position == 1) {newNode>next = head;head = newNode;return;}Node temp = head;int count = 1;while (temp!= NULL && count < position 1) {temp = temp>next;count++;}if (temp == NULL) {printf("位置无效\n");return;}newNode>next = temp>next;temp>next = newNode;}```4、删除节点删除头部节点```具体编程语言Node deleteAtHead(Node head) {if (head == NULL) {printf("链表为空,无法删除\n");return NULL;}Node temp = head;head = head>next;free(temp);return head;}```删除尾部节点```具体编程语言void deleteAtTail(Node head) {if (head == NULL) {printf("链表为空,无法删除\n");return;}Node prev = NULL;Node temp = head;while (temp>next!= NULL) {prev = temp;temp = temp>next;}if (prev == NULL) {head = NULL;} else {prev>next = NULL;}free(temp);}```删除指定节点```具体编程语言void deleteNode(Node head, int data) {Node prev = NULL;Node temp = head;while (temp!= NULL && temp>data!= data) {prev = temp;temp = temp>next;}if (temp == NULL) {printf("未找到要删除的数据\n");return;}if (prev == NULL) {head = temp>next;} else {prev>next = temp>next;}free(temp);}```5、查找节点```具体编程语言Node search(Node head, int data) {Node temp = head;while (temp!= NULL) {if (temp>data == data) {return temp;}temp = temp>next;}return NULL;}```6、打印单链表```具体编程语言void printList(Node head) {Node temp = head;while (temp!= NULL) {printf("%d ", temp>data);temp = temp>next;}printf("\n");}```五、实验结果1、成功创建了不同数据的单链表,并能够正确打印出链表中的数据。
单链表的实现及其基本操作
单链表的实现及其基本操作结点的引⼊链表是⼀种链式存储结构,链式存储结构的特点是⽤⼀组任意的存储单元存储数据元素。
为了能正确表⽰数据元素之间的线性关系,需引⼊结点概念。
⼀个结点表⽰链表中的⼀个数据元素,节点中除了储存数据元素的信息,还必须存放指向下⼀个节点的的指针(单、双链表的最后⼀个节点除外,它们存储的是⼀个空指针NULL)结点的结构如下图所⽰:代码如下:1 typedef struct node{2int data;3struct node* pNext;4 }Node, *PNode;View Code注:这⾥假设结点中储存的是整型 (int) 的数据单链表由多个结点依次连接⽽成,我们不难想象出它结构:我们注意到:在第⼀个结点的前⾯多了⼀个头结点,这是为了处理空表的⽅便⽽引⼊的,它的指针指向链表的第⼀个结点,⽽它的data域不存放任何信息。
单链表的基本操作1.创建链表1 PNode createList()2 {3int len, value;45 PNode pHead = (PNode)(malloc(sizeof(Node)));6 PNode pTail = pHead;7 pTail->pNext = NULL;89 printf("请输⼊你要的节点个数:");10 scanf("%d", &len);11for(int i=1;i<=len;i++){12 printf("请输⼊第%d个节点的值:", i);13 scanf("%d", &value);1415 PNode pNew = (PNode)malloc(sizeof(Node));16 pNew->data = value;17 pTail->pNext = pNew;18 pTail = pNew;19 pTail->pNext = NULL;20 }2122return pHead;23 }View Code2.遍历链表void traverse(PNode pHead){printf("遍历结果为:\n");PNode pTra = pHead;while(pTra->pNext != NULL){printf("%d ", pTra->pNext->data);pTra = pTra->pNext;}printf("\n");}View Code3.判断链表是否为空1bool isEmpty(PNode pHead)2 {3if(pHead->pNext==NULL)4return true;5else6return false;7 }View Code4.链表长度1int length(PNode pHead)2 {3int len = 0;4while(pHead->pNext!=NULL){5 pHead = pHead->pNext;6 len++;7 }8return len;910 }View Code5.插⼊结点1bool insert(PNode pHead, int pos, int val)2 {3if(pos<1 || pos>length(pHead)){4return false;5 }else{6 PNode pInsert = pHead;7for(int i=1;i<pos;i++){8 pInsert = pInsert->pNext;9 }1011 PNode pNew = (PNode)malloc(sizeof(Node));12 pNew->data = val;13 pNew->pNext = pInsert->pNext;14 pInsert->pNext = pNew;1516return true;17 }1819 }View Code6.删除结点1bool del(PNode pHead, int pos)2 {3if(pos<1 || pos>length(pHead)){4return false;5 }else{6 PNode pDel = pHead;7for(int i=1;i<pos;i++){8 pDel = pDel->pNext;9 }1011if(pos==length(pHead)){12free(pDel->pNext);13 pDel->pNext = NULL;14 }else{15 PNode pNext = pDel->pNext->pNext;16free(pDel->pNext);17 pDel->pNext = pNext;18 }1920return true;2122 }232425 }View Code7.查找节点(1)按元素值查找1 PNode locate(PNode pHead, int value)2 {3 PNode p = pHead->pNext;4while(p&&p->data!=value){ //NULL 是 05 p = p->pNext;6 }7return p;8 }View Code(2)按序号查找1 PNode get(PNode pHead, int k)2 {3 PNode p = pHead;4for(int i=1;i<=k;i++){5 p = p->pNext;6 }7return p;89 }View Code完整代码1 #include<stdio.h>2 #include<stdlib.h>3 typedef struct node{4int data;5struct node* pNext;6 }Node, *PNode;78 PNode createList();9void traverse(PNode pHead);10bool isEmpty(PNode pHead);11int length(PNode pHead);12bool insert(PNode pHead, int pos, int val);13bool del(PNode pHead, int pos);14 PNode get(PNode pHead, int k); //按序号查找15 PNode locate(PNode pHead, int value);//按值查找 1617int main(void)18 {19//test2021return0;22 }2324 PNode createList()25 {26int len, value;2728 PNode pHead = (PNode)(malloc(sizeof(Node)));29 PNode pTail = pHead;30 pTail->pNext = NULL;3132 printf("请输⼊你要的节点个数:");33 scanf("%d", &len);34for(int i=1;i<=len;i++){35 printf("请输⼊第%d个节点的值:", i);36 scanf("%d", &value);3738 PNode pNew = (PNode)malloc(sizeof(Node));39 pNew->data = value;40 pTail->pNext = pNew;41 pTail = pNew;42 pTail->pNext = NULL;43 }4445return pHead;46 }474849void traverse(PNode pHead)50 {51 printf("遍历结果为:\n");52 PNode pTra = pHead;53while(pTra->pNext != NULL)54 {55 printf("%d ", pTra->pNext->data);56 pTra = pTra->pNext;57 }58 printf("\n");59 }6061bool isEmpty(PNode pHead)62 {63if(pHead->pNext==NULL)64return true;65else66return false;67 }6869int length(PNode pHead)70 {71int len = 0;72while(pHead->pNext!=NULL){73 pHead = pHead->pNext;74 len++;75 }76return len;7778 }7980bool insert(PNode pHead, int pos, int val)81 {82if(pos<1 || pos>length(pHead)){83return false;84 }else{85 PNode pInsert = pHead;86for(int i=1;i<pos;i++){87 pInsert = pInsert->pNext;88 }8990 PNode pNew = (PNode)malloc(sizeof(Node));91 pNew->data = val;92 pNew->pNext = pInsert->pNext;93 pInsert->pNext = pNew;9495return true;96 }9798 }99100bool del(PNode pHead, int pos)101 {102if(pos<1 || pos>length(pHead)){103return false;104 }else{105 PNode pDel = pHead;106for(int i=1;i<pos;i++){107 pDel = pDel->pNext;108 }109110if(pos==length(pHead)){111free(pDel->pNext);112 pDel->pNext = NULL;113 }else{114 PNode pNext = pDel->pNext->pNext;115free(pDel->pNext);116 pDel->pNext = pNext;117 }118119return true;120121 }122123124 }125126 PNode get(PNode pHead, int k)127 {128 PNode p = pHead;129for(int i=1;i<=k;i++){130 p = p->pNext;131 }132return p;133134 }135 PNode locate(PNode pHead, int value)136 {137 PNode p = pHead->pNext;138while(p&&p->data!=value){ //NULL 是 0 139 p = p->pNext;140 }141return p;142 }View Code。
单链表的类型定义与基本操作
• 基本思想
• 找到第i个结点 • 从单链表上摘除该结点(修改某些结点的指针域)
L
a1
… ai-1
× ai
ai+1
…
a NULL
n
L
a1
… ai-1
ai+1
…
a NULL
n
12
• 算法
void delete_lklist(lklist &l , int i)
{ lklist p,q;
p=find_lklist(l, i-1);
• C语言类型描述
typedef struct node{
datatype
data; /*数据元素类型*/
struct node *next; /*指针类型*/
} node, * lklist; /*结点类型*/
• node是结点类型 • lklist是指向node类型的指针
1
二、一些基本操作
1. 初始化 initiate_lklist(l)
else printf("不存在第i个结点");
}
13
}
return (j); }
3
3. 按序号查找 find_lklist(l, i) • 定义
• 查找单链表第i个元素,否则返回NULL
• 基本思想
• 从头指针出发,顺链域next逐个往下搜索,直到 找到第i个结点为止
4
• 算法
node *find_lklist(lklist l, int i)
{ lklist p=l;
e
ai
…
a1n0 NULL
• 算法
void insert_lklist(lklist &l , datatype x, int i)
单链表的 基本操作
单向链表单向链表的基本操作,创建一个由6个节点组成的单向链表,显示链表中每个节点的数据,并且做增加、删除、查找节点以及计算单链表的长度等处理。
➢需求分析:1.功能(1)用尾插法创建一带头结点的由6个节点组成的单向链表:从键盘读入一组整数,作为单链表中的元素,输入完第6个结点后结束;将创建好的单链表元素依次输出到屏幕上。
(2)显示链表中每个节点的数据(3)从键盘输入一个数,查找在以上创建的单链表中是否存在该数;如果存在,显示它的位置,即第几个元素;如果不存在,给出相应提示如“No found node!”。
(4)在上述的单链表中的指定位置插入指定数据,并输出单链表中所有数据.(5)删除上述单链表中指定位置的结点,并输出单链表中所有数据.(6)求单链表的长度并输出。
2.输入要求先输入单链表中结点个数n,再输入单链表中所有数据,在单链表中需查找的数据,需插入的数据元素的位置、值,要删除的数据元素的位置。
3。
测试数据单链表中所有数据:12,23,56,21,8,10在单链表中需查找的数据:56;24插入的数据元素的位置、值:1,28;7,28;0,28要删除的数据元素的位置:6➢概要设计:1.算法思想:由于在操作过程中要进行插入、删除等操作,为运算方便,选用带头结点的单链表作数据元素的存储结构。
对每个数据元素,由一个数据域和一个指针域组成,数据域放输入的数据值,指针域指向下一个结点。
2.数据结构:单链表结点类型:typedef struct Liistnode {int data;struct Listnode *next;} NODE;3.模块划分:a)用尾插法建立带头结点的单链表*CreateList函数;b)显示链表中每个结点的数据PrintList函数;c)从键盘输入一个数,查找单链表中是否存在该数FoundList函数;d)在单链表中指定位置插入指定数据并输出单链表中所有数据InsertList函数;e)删除单链表中指定位置的结点并输出单链表中所有数据DeleteList函数;f)计算单链表的长度并在屏幕上输出LengthList函数;g)主函数main(),功能是给出测试数据值,建立测试数据值的带头结点的单链表,调用PrintList函数、FoundList函数、InsertList函数、DeleteList函数、LengthList函数实现问题要求.四、实验要求1.用C完成算法设计和程序设计并上机调试通过。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
单链表的定义及基本操作一、实验目的、意义(1)理解线性表中带头结点单链表的定义和逻辑图表示方法。
(2)熟练掌握单链表的插入,删除和查询算法的设计与实现。
(3)根据具体问题的需要,设计出合理的表示数据的链表结构,并设计相关算法。
二、实验内容及要求说明1:本次实验中的链表结构均为带头结点的单链表。
说明2: 学生在上机实验时,需要自己设计出所涉及到的函数,同时设计多组输入数据并编写主程序分别调用这些函数,调试程序并对相应的输出作出分析;修改输入数据,预期输出并验证输出的结果,加深对有关算法的理解。
具体要求:建立单链表,完成链表(带表头结点)的基本操作:建立链表、插入、删除、查找、输出;其它基本操作还有销毁链表、将链表置为空表、求链表的长度、获取某位置结点的内容、搜索结点。
三、实验所涉及的知识点数据结构、C语言语法函数、结构体类型指针、单链表(建表、初始化链表、求表长、插入、删除、查询算法)等。
四、实验结果及分析(所输入的数据及相应的运行结果,运行结果要有提示信息,运行结果采用截图方式给出。
)五、总结与体会(调试程序的心得与体会,若实验课上未完成调试,要认真找出错误并分析原因等。
)调试程序时,出现了许多错误。
如:结构体类型指针出错,忽略了释放存储空间,对头插法建表、尾插法建表不熟悉等。
另外还有一些语法上的错误。
由于对所学知识点概念模糊,试验课上未能完成此次上机作业。
后来经过查阅教材,浏览网页等方式,才完成试验。
这次试验出现错误最重要的原因就是对课本知识点理解不深刻以及编写代码时的粗心。
以后要都去练习、实践,以完善自己的不足。
六、程序清单(包含注释)//单链表#include<>#include<>#define OK 1#define ERROR 0typedef char ElemType;typedef int Status;//线性表的单链表的存储结构typedef struct LNode{ElemType data;struct LNode *next;}LNode,*LinkList;//LinkList为结构体类型的指针,可以直接定义变量,比如LinkList p;//建表(头插法)void CreatListF(LinkList &L,ElemType a[],int n){//初始化线性表L=(LinkList)malloc(sizeof(LNode));//分配内存空间L->next=NULL;//在表中插入元素LinkList S;int i;//头插法for(i=0;i<n;i++){S=(LinkList)malloc(sizeof(LNode));//生成新结点S->data=a[i];//数据域S->next=L->next;L->next=S;}}//建表(尾插法)void CreatListR(LinkList &L,ElemType a[],int n){L=(LinkList)malloc(sizeof(LNode));L->next=NULL;LinkList p;p=L;LinkList S;int i;//尾插法for(i=0;i<n;i++){S=(LinkList)malloc(sizeof(LNode));S->data=a[i];p->next=S;p=S;}p->next=NULL;}//初始化线性表void InitList(LinkList &L){L=(LinkList)malloc(sizeof(LNode));L->next=NULL;}//获得链表元素Status GetElem(LinkList L,int i,ElemType &e){//L为带头结点的单链表的头指针LinkList p;int j;//初始化,p指向第一个结点p=L->next;//j为计数器j=1;//顺指针往后查找,直到p指向第i个元素或p为空while(p && j<i){p=p->next;j++;}//第i个元素不存在if(!p || j>i)return ERROR;//取第i个元素e=p->data;return OK;}//插入Status ListInsert(LinkList &L,int i,ElemType e){int j=0;LinkList p;p=L;while(p!=NULL && j<i-1)//找第i-1个结点{p=p->next;j++;}if(!p || j>i-1)return ERROR;LinkList S;S=(LinkList)malloc(sizeof(LNode));//生成新结点S->data=e;S->next=p->next;p->next=S;return OK;}//删除Status ListDelete(LinkList &L,int i,ElemType &e){LinkList p;LinkList q;int j=0;p=L;while((p->next)!=NULL && j<i-1)//找第i个结点{p=p->next;j++;}//!(p->next) :指向第i个结点的指针为空(第i个元素不存在)if(!(p->next) || j>i-1)return ERROR;q=p->next;p->next=q->next;e=q->data;free(q);return OK;}//求表的长度int ListLength(LinkList L){LinkList p;p=L;int j=0;//线性链表最后一个结点的指针为空while((p->next)!=NULL){j++;p=p->next;}return j;}//输出void visit(LinkList L){LinkList p;p=L->next;while(p!=NULL){printf("%c ",p->data);p=p->next;}}//销毁:要销毁的话从头结点开始依次free 但要先得到下一个节点再free void DestroyList(LinkList &L){LinkList p;LinkList q;p=L;q=p->next;while(p!=NULL){free(p);p=q;q=p->next;}// free(p);}//判空int ListEmpty(LinkList L){//为空表则执行该语句,否则返回return 0;return (L->next==NULL);}//查找int ListSearch(LinkList L,ElemType e){LinkList p;p=L->next;int i=1;while(p!=NULL && p->data!=e){p=p->next;i++;}if(p==NULL)return 0;return i;}int main(){ElemType e;ElemType a[6]={'a','b','c','d','e','f'};LinkList L;//链表的头指针printf("头插法建表:");CreatListF(L,a,6);visit(L);printf("\n\n");//初始化InitList(L);printf("初始化后的表:");visit(L);printf("\n\n");printf("尾插法建表:");CreatListR(L,a,6);visit(L);printf("\n\n");//初始化后表为空,此时不要调用GetElem()GetElem(L,3,e);printf("表中第3个元素为:");printf("%c\n\n",e);//在第5个位置插入字符'k'ListInsert(L,5,'k');printf("在表中第5个位置插入字符'k'后:");visit(L);printf("\n\n");printf("表的长度为:%d\n\n",ListLength(L));int z;z=ListSearch(L,'d');printf("d是第%d个元素\n\n",z);ListDelete(L,2,e);printf("删除第2个元素:%c\n\n",e);//销毁// DestroyList(L);return 0;}。