单向链表(单链表)是链表的一种,其特点是链表的链接方向是单向的,对链表的访问要通过顺序读取从头部开始;链表是使用指针进行构造的列表;又称为结点列表,因为链表是由一个个结点组装起来的;其中每个结点都有指针成员变量指向列表中的下一个结点。
相比较普通的线性结构:
(1)单个结点创建非常方便,普通的线性内存通常在创建的时候就需要设定数据的大小
(2)结点的删除非常方便,不需要像线性结构那样移动剩下的数据
(3)结点的访问方便,可以通过循环或者递归的方法访问到任意数据,但是平均的访问效率低于线性表
代码:
#define _CRT_SECURE_NO_WARNINGS
#include "iostream"
#include "string"
using namespace std;
typedef struct Person
{
char name[32];
int age;
}DATATYPE;
typedef struct Node
{
DATATYPE data;
Node *next;
}linkNode;
typedef struct List
{
linkNode *head;
int clen;
}linkList;
//链表初始化
linkList* initList()
{
linkList* mlist = new linkList;
if (NULL == mlist)
{
perror("list init");
exit(1);
}
mlist->clen = 0;
mlist->head = NULL;
return mlist;
}
//头插
int insertHead(linkList* mlist,DATATYPE *mdata)
{
linkNode* newnode = new linkNode;
if (NULL == newnode)
{
perror("insertHead newnode");
return 1;
}
newnode->data = *mdata;
newnode->next = NULL;
newnode->next = mlist->head;
mlist->head = newnode;
mlist->clen++;
return 0;
}
//尾插
int insertTail(linkList *mlist, DATATYPE *mdata)
{
linkNode* newnode = new linkNode;
if (NULL == newnode)
{
perror("insertTail newnode");
return 1;
}
newnode->data = *mdata;
newnode->next = NULL;
if (NULL == mlist->head)
{
mlist->head = newnode;
}
else
{
linkNode* tmp = mlist->head;
while (tmp->next)
{
tmp = tmp->next;
}
tmp->next = newnode;
}
mlist->clen++;
return 0;
}
//删除指定数据
int delList(linkList *mlist, char *pname)
{
if (NULL == mlist->head) //判断链表是否为空
{
cout << "链表已为空" << endl;
return 1;
}
if (NULL == mlist->head->next)
{
if (0 == strcmp(mlist->head->data.name,pname)) //若只有表头,且表头数据为要删除的数据,则删除表头
{
delete mlist->head;
mlist->head = NULL;
return 0;
}
else
{
cout << "该数据不存在" << endl;
return 1;
}
}
else
{
linkNode *p = mlist->head;
linkNode *q = mlist->head;
while (p)
{
if (0 == strcmp(p->data.name,pname)) //查看第一个结点是不是要删除的数据
{
if (p == q)
{
mlist->head = p->next;
}
else
{
q->next = p->next;
}
delete p;
mlist->clen--;
return 0;
}
else
{
q = p;
p = p->next;
}
}
}
cout << "未找到要删除的元素" << endl;
return 1;
}
//删除链表
int destoryList(linkList *mlist)
{
linkNode *tmp;
while (mlist->head)
{
tmp = mlist->head;
mlist->head = tmp->next;
delete tmp;
tmp = NULL;
}
delete mlist;
mlist = NULL;
cout << "释放完成" << endl;
return 0;
}
//查找
linkNode* findList(linkList *mlist, char* pname)
{
linkNode *tmp = mlist->head;
while (tmp)
{
if (0 == strcmp(tmp->data.name,pname))
{
return tmp;
}
tmp = tmp->next;
}
cout << "此人不在链表中。。。" << endl;
return NULL;
}
//链表逆序
int reverseList(linkList *mlist)
{
linkNode *p = mlist->head->next;
linkNode *q = mlist->head;
while (p) //头插法
{
q->next = p->next;
p->next = mlist->head;
mlist->head = p;
p = q->next;
}
return 0;
}
//链表排序
int sortList(linkList *mlist)
{
if (NULL == mlist->head)
{
cout << "链表为空" << endl;
}
if (NULL == mlist->head->next)
{
cout << "链表只有一个表头" << endl;
}
else
{
linkNode *p, *q, tmp;
q = mlist->head;
while (q->next != NULL)
{
p = q->next;
while (p != NULL)
{
if (p->data.age < q->data.age)
{
tmp.data = p->data;
p->data = q->data;
q->data = tmp.data;
}
p = p->next;
}
q = q->next;
}
}
return 0;
}
//修改链表元素
int updataList(linkList *mlist,char *oldname,char *newname)
{
linkNode *tmp;
tmp = findList(mlist, oldname);
strcpy(tmp->data.name, newname);
return 0;
}
//打印链表
int showList(linkList* mlist)
{
linkNode *tmp = mlist->head;
while(tmp)
{
cout << "名字:" << tmp->data.name << " " << "年龄:" << tmp->data.age << endl;
tmp = tmp->next;
}
return 0;
}
int main()
{
linkList *m_list = initList();
DATATYPE data1 = { "张三",15 };
DATATYPE data4 = { "王麻子",50 };
insertTail(m_list, &data4);
insertHead(m_list, &data1);
showList(m_list);
cout << "--------------------------------------------" << endl;
cout << "头插:" << endl;
DATATYPE data2[2] = {
{"李四",16},
{"王五",17}
};
insertHead(m_list, &data2[0]);
insertHead(m_list, &data2[1]);
cout << "当前链表长度:" << m_list->clen << endl;
showList(m_list);
cout << "--------------------------------------------" << endl;
cout << "尾插:" << endl;
DATATYPE data3[4] = {
{ "东邪", 20 },
{ "西毒", 21 },
{ "南帝", 22 },
{ "北丐", 23 },
};
insertTail(m_list, &data3[0]);
insertTail(m_list, &data3[1]);
insertTail(m_list, &data3[2]);
insertTail(m_list, &data3[3]);
cout << "链表排序:" << endl;
sortList(m_list);
cout << "当前链表长度:" << m_list->clen << endl;
showList(m_list);
cout << "--------------------------------------------" << endl;
cout << "查找:" ;
linkNode *res = findList(m_list, "张三");
if (res != NULL)
{
cout << "查到此人:" << res->data.name << " " << "此人年龄:" << res->data.age << endl;
}
cout << "--------------------------------------------" << endl;
cout << "修改链表元素:";
updataList(m_list, "李四", "赵六");
cout << "--------------------------------------------" << endl;
cout << "指定删除:" << "王麻子" << endl;
delList(m_list, "王麻子");
cout << "当前链表长度:" << m_list->clen << endl;
showList(m_list);
cout << "--------------------------------------------" << endl;
cout << "链表逆序:" << endl;
reverseList(m_list);
cout << "当前链表长度:" << m_list->clen << endl;
showList(m_list);
destoryList(m_list);
system("pause");
return 0;
}