???????C語言實(shí)現(xiàn)單鏈表基本操作方法
存儲(chǔ)結(jié)構(gòu)
typedef int dataType;//愛護(hù)據(jù)類型
typedef struct Node {
DataType data; // 結(jié)點(diǎn)數(shù)據(jù)
struct Node *next; // 指向下一個(gè)結(jié)點(diǎn)的指針
} Node, *LinkList;基本功能
- 頭插法創(chuàng)建單鏈表void CreateListHead( LinkList &head)
- 尾插法創(chuàng)建單鏈表void CreateListTail( LinkList &head)
- 獲取指定位置的元素 int GetElement(LinkList head, int i, DataType &e)
- 獲取指定元素的位置 int LocateElement(LinkList head, int e)
- 在指定位置插入元素 int InsertList(LinkList head, int i, DataType e)
- 刪除指定位置的元素 int DeleteList(LinkList head, int i, DataType &e)
- 獲取單鏈表的長(zhǎng)度 int LengthLinkList(LinkList head)
- 合并兩個(gè)非遞減的單鏈表 void MergeList(LinkList La, LinkList Lb, LinkList &Lc)
- 寂鏈表void Destroy( LinkList &L)
- 遍歷打印單鏈表中的所有元素 void PrintList(LinkList head)
頭插法創(chuàng)建單鏈表
每次添加鏈的結(jié)點(diǎn)都能找到頭結(jié)點(diǎn)的第1號(hào)位置,所以創(chuàng)建單表中的元素的順序是輸入元素的逆序。 ?
/**
* 頭插法創(chuàng)建單鏈表,輸入以-1結(jié)束
*/
void CreateListHead(LinkList &head) {
DataType x;
LinkList p;
head = (LinkList)malloc(LEN);
head->next = NULL;
scanf("%d", &x);
while (x != -1) {
p = (LinkList)malloc(LEN);
p->data = x;
p->next = head->next; // 新增的結(jié)點(diǎn)指向頭結(jié)點(diǎn)的下一個(gè)結(jié)點(diǎn)
head->next = p; // 頭結(jié)點(diǎn)指向新增的結(jié)點(diǎn)
scanf("%d", &x);
}
}尾插法創(chuàng)建單鏈表
每次新增的結(jié)點(diǎn)都放在單鏈表的后面,接下來和接下來的順序保持一致。 ?
/**
* 尾插法創(chuàng)建單鏈表,輸入以-1結(jié)束
*/
void CreateListTail(LinkList &head) {
LinkList p, q;
DataType x;
head = (LinkList)malloc(LEN);
q = head;
scanf("%d", &x);
while (x != -1) {
p = (LinkList)malloc(LEN);
p->data = x;
q->next = p;
q = p;
scanf("%d", &x);
}
q->next = NULL;
}獲取指定位置的元素
/**
* 獲取指定位置的元素
* @param head 指向單鏈表頭結(jié)點(diǎn)的指針(頭指針)
* @param i 位置
* @param e 用來存放對(duì)應(yīng)位置的元素值
* @return 0:獲取失??;1:獲取成功
*/
int GetElement(LinkList head, int i, DataType &e) {
LinkList p = head->next;
int j = 1;
while (p && j < i) { // 依次后移,直至為空或到達(dá)位置
p = p->next;
j++;
}
if (!p || j > i) { // p為空表示位置超過最大位置,j > i表示位置不合法(i < 1)
return 0;
}
e = p->data;
return 1;
}在指定位置插入元素
/**
* 在單鏈表插入元素到位置i
* @param head 單鏈表的頭指針
* @param i 插入位置
* @param e 插入元素
* @return 1:插入成功,0:插入失敗
*/
int InsertList(LinkList head, int i, DataType e) {
LinkList p = head; // 從頭結(jié)點(diǎn)開始
int j = 1;
while (p && j < i) { // 找到插入位置的前一個(gè)結(jié)點(diǎn)
p = p->next;
j++;
}
if (!p || j > i) { // p為空或i < 1,插入位置不合法
return 0;
}
LinkList q = (LinkList)malloc(LEN); // 創(chuàng)建新結(jié)點(diǎn)
q->data = e;
q->next = p->next; // 將新結(jié)點(diǎn)指向前一個(gè)結(jié)點(diǎn)的后一個(gè)結(jié)點(diǎn)
p->next = q; // 前一個(gè)結(jié)點(diǎn)指向新結(jié)點(diǎn)
// 執(zhí)行上述兩個(gè)操作后,達(dá)到的效果是新結(jié)點(diǎn)插入到了前一個(gè)結(jié)點(diǎn)的后面
}刪除指定位置的元素
/**
* 刪除指定位置的元素
* @param head
* @param i 位置
* @param e 被刪除的元素的值存放在e中
* @return 1:刪除成功,0:刪除失敗
*/
int DeleteList(LinkList head, int i, DataType &e) {
LinkList p = head;
int j = 1;
while (p && j < i) { // 找到位置的前一個(gè)結(jié)點(diǎn)
p = p->next;
j++;
}
if (!p || j > i) {
return 0;
}
LinkList s = p->next;
e = s->data;
p->next = s->next; // 改變前一個(gè)結(jié)點(diǎn)的指向,使其指向刪除結(jié)點(diǎn)的后一個(gè)結(jié)點(diǎn)
free(s);
return 1;
}獲取單鏈表的長(zhǎng)度
/**
* 獲取單鏈表的長(zhǎng)度
* @param head
* @return 單鏈表的長(zhǎng)度
*/
int LengthLinkList(LinkList head) {
LinkList p = head->next;
int count = 0;
while (p) {
count++;
p = p->next;
}
return count;
}合并兩個(gè)非遞減的單鏈表
合并兩個(gè)非遞減的單鏈,新鏈表仍然保持非遞減。 ?
/**
* 合并兩個(gè)非遞減的單鏈表,新的鏈表仍然非遞減
* @param La
* @param Lb
* @param Lc
*/
void MergeList(LinkList La, LinkList Lb, LinkList &Lc) {
LinkList pa, pb, pc;
pa = La->next;
pb = Lb->next;
pc = Lc = (LinkList)malloc(LEN);
while (pa && pb) {
if (pa->data <= pb->data) {
pc->next = pa;
pc = pa;
pa = pa->next;
} else {
pc->next = pb;
pc = pb;
pb = pb->next;
}
}
pc->next = pa ? pa : pb;
free(Lb);
}晴鏈表
/**
* 銷毀鏈表
*/
void Destroy(LinkList &L) {
LinkList p, q;
p = L;
while (p) { // 遍歷所有結(jié)點(diǎn),釋放內(nèi)存
q = p;
p = p->next;
free(q);
}
L = NULL; // L置為NULL
}
遍歷打印單鏈表
/**
* 遍歷打印單鏈表的所有元素
*/
void PrintList(LinkList head) {
LinkList p = head->next;
if (p == NULL) {
cout << "List is NULL!" <<endl;
} else {
while (p != NULL) {
printf("%d ", p->data);
p = p->next;
}
printf("\n");
}
}
附上完整代碼
#include<cstdlib>
using namespace std;
#define LEN sizeof(Node)
typedef int DataType;
typedef struct Node {
DataType data;
struct Node *next;
} Node, *LinkList;
/**
* 頭插法創(chuàng)建單鏈表
* @param head
*/
void CreateListHead(LinkList &head) {
DataType x;
LinkList p;
head = (LinkList)malloc(LEN);
head->next = NULL;
scanf("%d", &x);
while (x != -1) {
p = (LinkList)malloc(LEN);
p->data = x;
p->next = head->next;
head->next = p;
scanf("%d", &x);
}
}
/**
* 尾插法創(chuàng)建單鏈表
* @param head
*/
void CreateListTail(LinkList &head) {
LinkList p, q;
DataType x;
head = (LinkList)malloc(LEN);
q = head;
scanf("%d", &x);
while (x != -1) {
p = (LinkList)malloc(LEN);
p->data = x;
q->next = p;
q = p;
scanf("%d", &x);
}
q->next = NULL;
}
/**
* 獲取指定位置的元素
* @param head 單鏈表頭指針
* @param i 位置
* @param e 獲取的元素賦值該參數(shù)
* @return 0:獲取失??;1:獲取成功
*/
int GetElement(LinkList head, int i, DataType &e) {
LinkList p = head->next;
int j = 1;
while (p && j < i) {
p = p->next;
j++;
}
if (!p || j > i) {
return 0;
}
e = p->data;
return 1;
}
/**
* 獲取某個(gè)元素的位置
* @param head
* @param e
* @return 元素的位置
*/
int LocateElement(LinkList head, int e) {
LinkList p = head->next;
int j = 1;
while (p && p->data != e) {
p = p->next;
j++;
}
if (!p) {
return 0;
}
return j;
}
/**
* 在單鏈表插入元素到位置i
* @param head 單鏈表的頭指針
* @param i 插入位置
* @param e 插入元素
* @return 1:插入成功,0:插入失敗
*/
int InsertList(LinkList head, int i, DataType e) {
LinkList p = head;
int j = 1;
while (p && j < i) {
p = p->next;
j++;
}
if (!p || j > i) {
return 0;
}
LinkList q = (LinkList)malloc(LEN);
q->data = e;
q->next = p->next;
p->next = q;
}
/**
* 刪除指定位置的元素
* @param head
* @param i 位置
* @param e 被刪除的元素的值存放在e中
* @return 1:刪除成功,0:刪除失敗
*/
int DeleteList(LinkList head, int i, DataType &e) {
LinkList p = head;
int j = 1;
while (p && j < i) {
p = p->next;
j++;
}
if (!p || j > i) {
return 0;
}
LinkList s = p->next;
e = s->data;
p->next = s->next;
free(s);
return 1;
}
/**
* 獲取單鏈表的長(zhǎng)度
* @param head
* @return
*/
int LengthLinkList(LinkList head) {
LinkList p = head->next;
int count = 0;
while (p) {
count++;
p = p->next;
}
return count;
}
/**
* 合并兩個(gè)非遞減的單鏈表,新的鏈表仍然非遞減
* @param La
* @param Lb
* @param Lc
*/
void MergeList(LinkList La, LinkList Lb, LinkList &Lc) {
LinkList pa, pb, pc;
pa = La->next;
pb = Lb->next;
pc = Lc = (LinkList)malloc(LEN);
while (pa && pb) {
if (pa->data <= pb->data) {
pc->next = pa;
pc = pa;
pa = pa->next;
} else {
pc->next = pb;
pc = pb;
pb = pb->next;
}
}
pc->next = pa ? pa : pb;
free(Lb);
}
/**
* 銷毀鏈表
* @param L
*/
void Destroy(LinkList &L) {
LinkList p, q;
p = L;
while (p) {
q = p;
p = p->next;
free(q);
}
L = NULL;
}
/**
* 遍歷打印單鏈表的所有元素
* @param head
*/
void PrintList(LinkList head) {
LinkList p = head->next;
if (p == NULL) {
cout << "List is NULL!" <<endl;
} else {
while (p != NULL) {
printf("%d ", p->data);
p = p->next;
}
printf("\n");
}
}
int main() {
LinkList L;
printf("頭插法創(chuàng)建單鏈表:(輸入以-1結(jié)束)\n");
CreateListHead(L);
PrintList(L);
printf("尾插法創(chuàng)建單鏈表:(輸入以-1結(jié)束)\n");
CreateListTail(L);
PrintList(L);
InsertList(L, 1, 100);
printf("在1號(hào)位置插入100后,單鏈表如下:\n");
PrintList(L);
DataType e;
DeleteList(L, 1, e);
printf("刪除1號(hào)位置的元素,被刪除的元素為:\n");
printf("刪除后的單鏈表為:\n");
PrintList(L);
printf("單鏈表的長(zhǎng)度為:%d\n", LengthLinkList(L));
GetElement(L, 1, e);
printf("1號(hào)位置的元素為:%d\n");
printf("元素4在單鏈表中的位置為:%d\n", LocateElement(L, 4));
cout << endl;
LinkList La, Lb, Lc;
printf("尾插法創(chuàng)建單鏈表La:\n");
CreateListTail(La);
PrintList(La);
printf("尾插法創(chuàng)建單鏈表Lb:\n");
CreateListTail(Lb);
PrintList(Lb);
MergeList(La, Lb, Lc);
printf("合并單鏈表La和Lb后的新單鏈表Lc如下:\n");
PrintList(Lc);
return 0;
}運(yùn)行結(jié)果:

注意:
寫法采用了C++引用參數(shù)的寫法,LinkList &head,C語言下不支持這種寫法,需要在C++環(huán)境下使用,即.cpp文件。
下面附上C語言的:
/**
* LinkList 本身已經(jīng)是結(jié)構(gòu)體指針,參數(shù)再使用LinkList *的形式
* 可以理解為要想改變一個(gè)結(jié)構(gòu)體指針,則需要取指針的指針。
* 類似于改變int a,則需要使用 int *a,這里要改變LinkList head,則需要使用LinkList *head
*/
void CreatListTail(LinkList *head) {
int x;
LinkList *p, *q;
*head = (LinkList *) malloc(LEN);
q = *head;
scanf("%d", &x);
while (x != -1) {
p = (LinkList *) malloc(LEN);
p->data = x;
q->next = p;
q = p;
scanf("%d", &x);
}
q->next = NULL;
}
// 可以不傳參,函數(shù)里面定義頭指針,創(chuàng)建鏈表,然后把頭指針返回,主函數(shù)用結(jié)構(gòu)體指針接收即可
LinkList CreateListhead() {
int x;
LinkList *head, *p;
head = (LinkList *) malloc(LEN);
head->next = NULL;
scanf("%d", &x);
while (x != -1) {
p = (LinkList *) malloc(LEN);
p->data = x;
p->next = head->next;
head->next = p;
}
return head;
}到此這篇關(guān)于C語言實(shí)現(xiàn)單鏈表基本操作方法的文章就介紹到這了,更多相關(guān)C語言單鏈表內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
C++實(shí)現(xiàn)LeetCode(50.求x的n次方)
這篇文章主要介紹了C++實(shí)現(xiàn)LeetCode(50.求x的n次方),本篇文章通過簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下2021-07-07
VSCode配置C++環(huán)境的方法步驟(MSVC)
這篇文章主要介紹了VSCode配置C++環(huán)境的方法步驟,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-05-05

