《資料結構與演算法》第一次實驗內容•線性表的建立、銷燬、插入、刪除、遍歷等操作的實現
《資料結構與演算法》第一次課內容安排
線性表的建立、銷燬、插入、刪除、遍歷等操作的實現
實驗目的:
1、通過實驗掌握、複習C++有關基本知識;
2、通過實驗熟練掌握在連結串列結構中實現線性表操作的方法,並實現基本操作:查詢、插入和刪除等演算法。
實驗內容:
一、連結串列概述:
連結串列是一種動態資料結構,特點是用一組任意的儲存單元(可以是連續的,也可以是不連續的)存放資料元素。連結串列中每一個元素稱為“結點”,每一個結點都是由資料域和指標域組成的,每個結點中的指標域指向下一個結點。Head是“頭指標”,表示連結串列的開始,用來指向第一個結點,而最後一個指標的指標域為NULL(空地址),表示連結串列的結束。可以看出連結串列結構必須利用指標才能實現,即一個結點中必須包含一個指標變數,用來存放下一個結點的地址。
二、實驗步驟(參考)
(一)、結點的定義
連結串列中的結點中只有一個指標的連結串列稱為單鏈表,這是最簡單的連結串列結構。可定義單鏈表結構的最簡單形式如下。
struct Node
{
int Data;
Node*next;//指標域,指向下一個結
};
這裡用到了結構體型別。其中,*next是指標域,用來指向該結點的下一個結點;Data是一個整形變數,用來存放結點中的資料。當然,Data可以是任何資料型別,包括結構體型別或類型別。
(二)、類的定義
class list { Node*head; public: list(){head=NULL;} void insertlist(int aData,int bData); void deletelist(int aData); void outputlist(); Node*gethead(){return head;} };
1.void outputlist();//連結串列結點的訪問輸出
由於連結串列中的各個結點是由指標連結在一起的,其儲存單元是連續的,因此,對其中任意結點的地址無法向陣列一樣,用一個簡單的公式計算出來,進行隨機訪問。只能從連結串列的頭指標(即head)開始,用一個指標p先指向第一個結點,然後根據結點p找到下一個結點。以此類推,直至找到所要訪問的結點或到最後一個結點(指標為空)為止。
2.void insertlist(int aData,int bData);//表結點的插入
如果要在連結串列中的結點a之前插入結點b,則需要考慮下面幾點情況:
(1) 插入前連結串列是一個空表,這時插入新結點b後。
(2) 若a是連結串列的第一個結點,則插入後,結點b為第一個結點。
(3) 若連結串列中存在a,且不是第一個結點,則首先要找出a的上一個結點,然後使上一個節點的指標域指向b,在令b的指標域指向a,即可完成插入
(4) 如連結串列中不存在a,則插在最後。先找到連結串列的最後一個結點,然後使的指標域指向結點b,而b指標的指標為空。
3. void deletelist(int aData);//表結點的刪除
如果要在連結串列中刪除結點a並釋放被刪除的結點所佔的儲存空間,則需要考慮下列幾種情況:
(1) 若要刪除的結點a是第一個結點,則把head指向a的下一個結點。
(2) 若要刪除的結點a存在於連結串列中,但不是第一個結點,則應使a的上一個結點的指標域指向a的下一個結點。
(3) 空表或要刪除的結點a不存在,則不做任何改變。
(三)、完成程式
下面的程式是本實驗的程式原始碼.
#include"iostream"
using namespace std;
struct Node
{
int Data;
Node*next;
};
class list
{
Node*head;
public:
list() { head = NULL; }
void insertlist(int aData, int bData);
void deletelist(int aData);
void outputlist();
Node*gethead() { return head; }
};
void list::insertlist(int aData, int bData) //設aData是結點a中的資料,bData是結點b中的資料,在a結點的前面插入b結點。
{
Node*p, *s; //p指向結點a,s指向結點b
s = (Node*)new(Node); //動態分配一個新結點
s->Data = bData; //設b為此結點
p = head;//p是一開始的頭結點
if (head == NULL)//(1)插入前連結串列是一個空表,這時插入新結點b後。
{
head = s;//頭結點為空,就讓頭結點指向b,結點b的指標域賦值空
s->next = NULL;
}
else
if (head->Data == aData)//(2) 若a是連結串列的第一個結點,則插入後,結點b為第一個結點。
{
s->next = p;
head = s;
}
else
{
while (p->next != NULL)//(3) 若連結串列中存在a,且不是第一個結點,則首先要找出a的上一個結點,然後使上一個節點的指標域指向b,在令b的指標域指向a,即可完成插入
{
if (p->next->Data == aData)
{
s->next = p->next;
p->next = s;
break;
}
p = p->next;
}
if (p->next == NULL)//(4) 如連結串列中不存在a,則插在最後。先找到連結串列的最後一個結點,然後使的指標域指向結點b,而b指標的指標為空。
{
p->next = s;
s->next = NULL;
}
}
}
void list::deletelist(int aData) //設aData是要刪除的結點a中的資料成員
{
Node*p; //p用於指向結點a
p = head;
if (head->Data == aData)
head = head->next;
else
while (p->next != NULL)
{
if (p->next->Data == aData)//迴圈找到這個結點,然後斷開鏈子,把兩頭連上,即可完成刪除中間的那個結點
{
p->next = p->next->next;
break;
}
p = p->next;
}
}
void list::outputlist() //輸出連結串列
{
Node *p;
p = head;
if (head != NULL)
{
cout << "新連結串列為:"<<head->Data;
while (p->next != NULL)
{
cout << p->next->Data;
p = p->next;
}
}
}
void main()
{
list L;
char option;
while (1)
{
cout << "\n連結串列操作練習:" << endl;
cout << "1: 建立連結串列" << endl;
cout << "2: 插入新節點" << endl;
cout << "3: 刪除節點" << endl;
cout << "4: 遍歷節點" << endl;
cout << "0: 退出" << endl;
cout << "\n請輸入你的選擇:";
cin >> option;
switch (option)
{
case'0':
exit(0);
break;
case'1':
break;
case'2':
int a, b;
cout << "請輸入要插入的位置的結點值(在其前面插入):" << endl;
cin >> a;
cout << "請輸入要插入的結點的值:" << endl;
cin >> b;
L.insertlist(a, b);
L.outputlist();
break;
case'3':
cout << "輸入要刪除的結點" << endl;
cin >> a;
L.deletelist(a);
L.outputlist();
break;
case '4':
L.outputlist();
break;
}
}
}
有問題請聯絡我 QQ:1239825268
備註:CSDN