单链表抽象数据类型
ADT 线性表(List)
Data
线性表的数据对象集合为{a1,a2,…,an},每个元素的类型均为DataType。其中,除了第一个元素a1外,
每个元素有且只有一个直接的前驱,除了最后一个元素,每个元素有且只有一个直接后继元素。数据
元素之间的关系是一对一的关系。
Operator
InitList(*L):初始化操作,建立一个空的线性表L
ListEmpty(L):若线性表为空,返回true,否则返回false
ClearList(*L):将线性表清空
GetElem(L,I,*e):将线性表L中第i个位置元素值返回给e
LocateElem(L,e):在线性表L中查找与给定值e相等的元素;查找成功,返回该元素在表中序号表示成功,
否则返回0表示失败,
ListInsert(*L,i,e):在线性表中的第i个位置插入新元素e
ListDelet(*L,i,*e):删除线性表L中第i个位置元素,并用e返回其值
ListLength(L):返回线性表L的元素个数
.hpp
#ifndef TEST_H_
#define TEST_H_
#include<malloc.h>
typedef int ElemType;
typedef struct Node
{
ElemType data;
struct Node * next;
}Node;
typedef struct Node * Linklist;
//InitList(*L) :初始化操作,建立一个空的线性表L
Linklist initList();
//ListEmpty(L) : 若线性表为空,返回true, 否则返回false
bool listEmpty(const Linklist L);
//ListLength(L) : 返回线性表L的元素个数
int listLength(Linklist L);
//ClearList(*L) : 将线性表清空
void clearList(Linklist L);
//GetElem(L, I, *e) : 将线性表L中第i个位置元素值返回给e
bool getElem(const Linklist L, const int i, ElemType * e);
//LocateElem(L, e) : 在线性表L中查找与给定值e相等的元素;查找成功,返回该元素在表中序号表示成功,否则返回0表示失败
bool locateElem(const Linklist L, ElemType e);
//ListInsert(*L, i, e) : 在线性表中的第i个位置插入新元素e
bool listInsert(Linklist L, const int i, ElemType e);
//ListDelet(*L,i,*e) : 删除线性表L中第i个位置元素,并用e返回其值
bool listDelete(Linklist L, const int i);
#endif // !TEST_H_
#pragma once
.cpp
#include"test.h"
//InitList(*L) :初始化操作,建立一个空的线性表L
Linklist initList() {
Linklist temp = (Linklist)malloc(sizeof(Linklist));
temp->next = nullptr;
return temp;
}
//ListEmpty(L) : 若线性表为空,返回true, 否则返回false
bool listEmpty(const Linklist L) {
Linklist p = L->next;
int length = 0;
while (p != nullptr)
{
p = p->next;
++length;
}
if (length == 0)
return true;
else
return false;
}
//ListLength(L) : 返回线性表L的元素个数
int listLength(Linklist L) {
Linklist p = L->next;
int length = 0;
while (p != nullptr)
{
p = p->next;
++length;
}
return length;
}
//ClearList(*L) : 将线性表清空
//(1)声明一个节点p和q
//(2)将第一个节点赋值给p
//(3)循环
// 将下一个节点赋给q
// 释放p
// 将q赋给p
void clearList(Linklist L) {
Linklist p, q;
p = L->next;
while (p != nullptr)
{
q = p->next;
free(p);
p = q;
}
L->next = nullptr;
}
//GetElem(L, I, *e) : 将线性表L中第i个位置元素值返回给e
//(1)声明一个指针p指向链表第一个结点,初始化j从1开始
//(2)当j<i时就遍历链表,让p的指针向后移动,不断指向下一个结点,j累加1
//(3)若到链表末尾P为空,则说明第i个结点不存在
//(4)否则查找成功,返回结点p的数据
bool getElem(const Linklist L, const int i, ElemType * e) {
Linklist p = L->next;
int j = 1;
while ((p != nullptr) && (j < i))
{
p = p->next;
++j;
}
if (p == nullptr || j > i)
return false;
*e = p->data;
return true;
}
//LocateElem(L, e) : 在线性表L中查找与给定值e相等的元素;查找成功,返回该元素在表中序号表示成功,否则返回0表示失败
bool locateElem(const Linklist L, ElemType e) {
Linklist p = L->next;
int j = 1;
while (p != nullptr)
{
if (e == p->data)
{
return j;
break;
}
p = p->next;
++j;
}
if (p == nullptr)
return 0;
}
//ListInsert(*L, i, e) : 在线性表中的第i个位置插入新元素e
//(1)声明一指针p指向链表头结点,初始化j从1开始
//(2)当j<i时,就遍历链表,让p的指针向后移动,不断指向下一个结点,j累加1
//(3)若到链表末尾p为空,则说明第i个结点不存在
//(4)否则查找成功,在系统中生成一个空结点s
//(5)将数据元素e赋给s->data
//(6)单链表插人标准语句s->next = p->next;p->next = s;
//(7)返回成功
bool listInsert(Linklist L, const int i, ElemType e) {
Linklist p = L,s;
int j = 1;
while (p != nullptr && j < i)
{
p = p->next;
++j;
}
if (p == nullptr || j > i)
return false;
s = (Linklist)malloc(sizeof(Linklist));
s->data = e;
s->next = p->next;
p->next = s;
return true;
}
//ListDelet(*L,i,*e) : 删除线性表L中第i个位置元素,并用e返回其值
//(1)声明一指针p指向链表头指针,初始化j从1开始
//(2)当j<i开始,就遍历链表,rangp的指针向后移动,不断指向下一个结点,j累加1
//(3)若到链表末尾p为空,这说明第i个结点不存在
//(4)否则查找成功,将欲删除的界定啊p->next赋值给q
//(5)单链表的删除标准语句p->next = q->next;
//(6)将q结点中的数据值赋给e,作为返回
//(7)释放q结点
//(8)返回成功
bool listDelete(Linklist L, const int i) {
Linklist p = L;
Linklist s;
int j = 1;
while (p != nullptr && j < i)
{
p = p->next;
++j;
}
if (p == nullptr || j > i)
return false;
s = p->next;
p->next = s->next;
free(s);
return true;
}
main函数
#include<iostream>
#include"test.h"
void showList(const Linklist L);
int main()
{
Linklist root = initList();
std::cout<<listEmpty(root)<<std::endl;
std::cout << listLength(root) << std::endl;
listInsert(root, 0, 1);
listInsert(root, 1, 2);
listInsert(root, 2, 3);
listInsert(root, 3, 4);
listInsert(root, 4, 5);
listInsert(root, 5, 6);
std::cout << "表的当前长度为: " << listLength(root) << std::endl;
std::cout << listEmpty(root) << std::endl;
showList(root);
clearList(root);
std::cout << "表的当前长度为: " << listLength(root) << std::endl;
std::cout << listEmpty(root) << std::endl;
listDelete(root, 2);
showList(root);
return 0;
}
void showList(const Linklist L) {
if(listLength(L) < 1)
std::cerr << "线性表为空表!\n";
else
{
Linklist p = L->next;
while (p != nullptr)
{
std::cout << p->data << " ";
p = p->next;
}
std::cout << std::endl;
}
}
运行结果: