大綱 單向鏈結串列 環狀串列 雙向鏈結串列 鏈結串列的應用.

Slides:



Advertisements
Similar presentations
FCU, Department of ECE, IC Design Research Lab. TEL: # 4945 Pre-SIm , Post-Sim.
Advertisements

Divide-and-Conquer. 什麼是 divide-and-conquer ? Divide 就是把問題分割 Conquer 則是把答案結合起來.
6-1 指標簡介 6-2 指標與陣列 6-3 動態配置記憶體 6-4 本章綜合練習
布林代數的應用--- 全及項(最小項)和全或項(最大項)展開式
第七章 抽樣與抽樣分配 蒐集統計資料最常見的方式是抽查。這 牽涉到兩個問題: 抽出的樣本是否具有代表性?是否能反應出母體的特徵?
資料的搜尋 搜尋的基本概念 循序搜尋法(Sequential Search) 二元搜尋法(Binary Search)
: A-Sequence 星級 : ★★☆☆☆ 題組: Online-judge.uva.es PROBLEM SET Volume CIX 題號: Problem D : A-Sequence 解題者:薛祖淵 解題日期: 2006 年 2 月 21 日 題意:一開始先輸入一個.
:Word Morphing ★★☆☆☆ 題組: Problem Set Archive with Online Judge 題號: 10508:word morphing 解題者:楊家豪 解題日期: 2006 年 5 月 21 日 題意: 第一行給你兩個正整數, 第一個代表下面會出現幾個字串,
1 Q10276: Hanoi Tower Troubles Again! 星級 : ★★★ 題組: Online-judge.uva.es PROBLEM SET Volume CII 題號: Q10276: Hanoi Tower Troubles Again! 解題者:薛祖淵 解題日期: 2006.
第6章 佇列(Queues) 6-1 佇列的基礎 6-2 佇列的表示法 6-3 環狀佇列 6-4 雙佇列.
1 第一章 Word 的基本觀念 內容概要: Word 的特色 啟動與離開 Word 的方法 滑鼠游標與外型的介紹 基本操作 Word 視窗法則 使用 Word 遭遇問題時, 應如何利用軟體特 性而獲得輔助解說.
1 Web of Science 利用指引 單元二 瀏覽與處理查詢結果. 2 瀏覽檢索結果 查出的結果,預設以時間排列, 使用者可改變結果的排列方式: 還可以依被引用次數、相關度、 第一作者、刊名、出版年等排序 回到前先查的結果畫面 點選想看資料的完整書目 本館訂購範圍的期刊 全文,便可直接連結.
Graph V(G 1 )={0, 1, 2, 3, 4, 5, 6, 7, 8, 9} E(G 1 )={(0, 2), (0, 3), (1, 4), (2, 3), (2, 5), (2, 6), (3, 6), (3, 7), (4, 7), (5, 6), (5,
:New Land ★★★★☆ 題組: Problem Set Archive with Online Judge 題號: 11871: New Land 解題者:施博修 解題日期: 2011 年 6 月 8 日 題意:國王有一個懶兒子,為了勞動兒子,他想了一個 辦法,令他在某天早上開始走路,直到太陽下山前,靠.
: OPENING DOORS ? 題組: Problem Set Archive with Online Judge 題號: 10606: OPENING DOORS 解題者:侯沛彣 解題日期: 2006 年 6 月 11 日 題意: - 某間學校有 N 個學生,每個學生都有自己的衣物櫃.
: ShellSort ★★☆☆☆ 題組: Problem D 題號: 10152: ShellSort 解題者:林一帆 解題日期: 2006 年 4 月 10 日 題意:烏龜王國的烏龜總是一隻一隻疊在一起。唯一改變烏龜位置 的方法為:一隻烏龜爬出他原來的位置,然後往上爬到最上方。給 你一堆烏龜原來排列的順序,以及我們想要的烏龜的排列順序,你.
STAT0_sampling Random Sampling  母體: Finite population & Infinity population  由一大小為 N 的有限母體中抽出一樣本數為 n 的樣 本,若每一樣本被抽出的機率是一樣的,這樣本稱 為隨機樣本 (random sample)
1. 假設以下的敘述為一未提供 “ 捷徑計算 ” 能力的程式段,試用程 式設計的技巧,使此敘述經此改 寫的動作後,具有與 “ 捷徑計算 ” 之 處理方法相同之處理模式。 if and then E1 else E2 endif.
JAVA 程式設計與資料結構 第十四章 Linked List. Introduction Linked List 的結構就是將物件排成一列, 有點像是 Array ,但是我們卻無法直接經 由 index 得到其中的物件 在 Linked List 中,每一個點我們稱之為 node ,第一個 node.
MATLAB 程式設計 第 11 章 多維陣列 多維陣列的定義 在 MATLAB 的資料型態中,向量可視為 一維陣列,矩陣可視二維陣列,對於維 度 (Dimensions) 超過 1 的陣列則均可視 為「多維陣列」 (Multidimesional Arrays , 簡稱 N-D Arrays)
程式註解說明. 2 程式註解格式 塊狀註解 對檔案、 class 、 method 、資料結構、一段程式 …. 等程式區塊 做說明。 第一行的開頭必需為 “/*” 且沒有其他文字,最後一行的開頭 必需以 “*/” 做為結束,在中間每一行的開頭都必需是一個 “*” 。 單行註解 佔據一整行的說明。 以.
8.1 何謂高度平衡二元搜尋樹 8.2 高度平衡二元搜尋樹的加入 8.3 高度平衡二元搜尋樹的刪除
: The Playboy Chimp ★★☆☆☆ 題組: Problem Set Archive with Online Judge 題號: 10611: The Playboy Chimp 解題者:蔡昇宇 解題日期: 2010 年 2 月 28 日 題意:給一已排序的數列 S( 升冪.
桁架分析.
具備人臉追蹤與辨識功能的一個 智慧型數位監視系統 系統架構 在巡邏模式中 ,攝影機會左右來回巡視,並 利用動態膚色偵測得知是否有移動膚色物體, 若有移動的膚色物體則進入到追蹤模式,反之 則繼續巡視。
第 1 章 PC 的基本構造. 本章提要 PC 系統簡介 80x86 系列 CPU 及其暫存器群 記憶體: Memory 80x86 的分節式記憶體管理 80x86 的 I/O 結構 學習組合語言的基本工具.
Introduction to Java Programming Lecture 17 Abstract Classes & Interfaces.
:Problem D: Bit-wise Sequence ★★★☆☆ 題組: Problem Set Archive with Online Judge 題號: 10232: Problem D: Bit-wise Sequence 解題者:李濟宇 解題日期: 2006 年 4 月 16.
第九章 結構. 結構的宣告 結構 它是由許多不同 ( 或相同 ) 資料型態的變數所組成的 集合,通常利用結構標籤稱呼此集合 struct student { char *name; int score; }; struct 為保留字,表示結構的宣告開始 結構項目需定義於大括號「 { } 」內 結尾需加上分號.
24-6 設定開始與結束場景中的 程式 最後我們要替這個遊戲收個尾, 幫它把開始 的等待畫面跟結束畫面處理一下。
: The largest Clique ★★★★☆ 題組: Contest Archive with Online Judge 題號: 11324: The largest Clique 解題者:李重儀 解題日期: 2008 年 11 月 24 日 題意: 簡單來說,給你一個 directed.
計算機概論 - 排序 1 排序 (Sorting) 李明山 編撰 ※手動換頁.
7 陣列與搜尋 7.1 陣列 一般資料變數 宣告一維陣列 起始一維陣列 7-4
圖層的操作與管理 圖層的作用就如同一張張透明的賽璐璐片, 你可以將動畫中的每項物件, 放置在不同圖 層中, 圖層交疊就形成完整的畫面。在各圖 層中的物件, 做任何的移動或變化, 都不會 相互干擾, 所以當你編輯一個物件時, 只要 在物件所在的圖層進行操作, 將可大幅降低 製作過程的複雜度與難度。
: Happy Number ★ ? 題組: Problem Set Archive with Online Judge 題號: 10591: Happy Number 解題者:陳瀅文 解題日期: 2006 年 6 月 6 日 題意:判斷一個正整數 N 是否為 Happy Number.
: Fast and Easy Data Compressor ★★☆☆☆ 題組: Problem Set Archive with Online Judge 題號: 10043: Fast and Easy Data Compressor 解題者:葉貫中 解題日期: 2007 年 3.
第十章 再論結構. 指標與結構的關係 /* File name: ex10-1a.c */ #include int main() { struct student { char *name; int score; }; struct student st= {"Brian", 97}; struct.
: Multisets and Sequences ★★★★☆ 題組: Problem Set Archive with Online Judge 題號: 11023: Multisets and Sequences 解題者:葉貫中 解題日期: 2007 年 4 月 24 日 題意:在這個題目中,我們要定義.
:Nuts for nuts..Nuts for nuts.. ★★★★☆ 題組: Problem Set Archive with Online Judge 題號: 10944:Nuts for nuts.. 解題者:楊家豪 解題日期: 2006 年 2 月 題意: 給定兩個正整數 x,y.
資料結構實習-一 參數傳遞.
第六章 陣列.
Lecture 7 Sorting in Linear Time. Sorting in Linear Time2 7.1 Lower bounds for sorting 本節探討排序所耗用的時間複雜度下限。 任何一個以比較為基礎排序的演算法,排序 n 個元 素時至少耗用 Ω(nlogn) 次比較。
1 Introduction to Java Programming Lecture 2: Basics of Java Programming Spring 2008.
4 堆疊與佇列 4.1 前言 四種基本的資料結構 (可儲存資料的容器) 陣列 (Array)、串列(List): 最基本
: Beautiful Numbers ★★★★☆ 題組: Problem Set Archive with Online Judge 題號: 11472: Beautiful Numbers 解題者:邱經達 解題日期: 2011 年 5 月 5 日 題意: 若一個 N 進位的數用到該.
: Lucky Number ★★★★☆ 題組: Proble Set Archive with Online Judge 題號: 10909: Lucky Number 解題者:李育賢 解題日期: 2008 年 4 月 25 日 題意:給一個奇數數列 1,3,5,7,9,11,13,15…
Section 4.2 Probability Models 機率模式. 由實驗看機率 實驗前先列出所有可能的實驗結果。 – 擲銅板:正面或反面。 – 擲骰子: 1~6 點。 – 擲骰子兩顆: (1,1),(1,2),(1,3),… 等 36 種。 決定每一個可能的實驗結果發生機率。 – 實驗後所有的實驗結果整理得到。
JAVA 程式設計與資料結構 第二十章 Searching. Sequential Searching Sequential Searching 是最簡單的一種搜尋法,此演 算法可應用在 Array 或是 Linked List 此等資料結構。 Sequential Searching 的 worst-case.
演算法 8-1 最大數及最小數找法 8-2 排序 8-3 二元搜尋法.
845: Gas Station Numbers ★★★ 題組: Problem Set Archive with Online Judge 題號: 845: Gas Station Numbers. 解題者:張維珊 解題日期: 2006 年 2 月 題意: 將輸入的數字,經過重新排列組合或旋轉數字,得到比原先的數字大,
Structural Equation Modeling Chapter 6 CFA 根據每個因素有多重指標,以減少 測量誤差並可建立問卷的構念效度 驗證性因素分析.
Learning Method in Multilingual Speech Recognition Author : Hui Lin, Li Deng, Jasha Droppo Professor: 陳嘉平 Reporter: 許峰閤.
Chapter 10 m-way 搜尋樹與B-Tree
本章重點 2-1 有序串列(Ordered List) 2-2 介紹陣列(array) 2-3 矩陣(matrix)的應用
Probability Distribution 機率分配 汪群超 12/12. 目的:產生具均等分配的數值 (Data) ,並以 『直方圖』的功能計算出數值在不同範圍內出現 的頻率,及繪製數值的分配圖,以反應出該 機率分配的特性。
1 Introduction to Java Programming Lecture 2: Basics of Java Programming Spring 2009.
中序轉後序 藉由由左向右掃瞄中序運算式產生後序運算式,遇到 運算元就直接輸出,遇到運算符號則先存入堆疊,將 優先權較高者輸出。 範例: a + b * c TokenStack [0] [1] [2] topoutput aa ++0a b+0ab *+ *1ab c+ *1abc eosabc*+
連續隨機變數 連續變數:時間、分數、重量、……
1 Introduction to Java Programming Lecture 3 Mathematical Operators Spring 2008.
1 Introduction to Java Programming Lecture 2: Basics of Java Programming Spring 2010.
: SAM I AM ★★★★☆ 題組: Contest Archive with Online Judge 題號: 11419: SAM I AM 解題者:李重儀 解題日期: 2008 年 9 月 11 日 題意: 簡單的說,就是一個長方形的廟裡面有敵人,然 後可以橫的方向開砲或縱向開砲,每次開砲可以.
: Finding Paths in Grid ★★★★☆ 題組: Contest Archive with Online Judge 題號: 11486: Finding Paths in Grid 解題者:李重儀 解題日期: 2008 年 10 月 14 日 題意:給一個 7 個 column.
:Problem E.Stone Game ★★★☆☆ 題組: Problem Set Archive with Online Judge 題號: 10165: Problem E.Stone Game 解題者:李濟宇 解題日期: 2006 年 3 月 26 日 題意: Jack 與 Jim.
幼兒行為觀察與記錄 第八章 事件取樣法.
第 1 章 PC 的基本構造. 本章提要 PC 系統簡介 80x86 系列 CPU 及其暫存器群 記憶體: Memory 80x86 的分節式記憶體管理 80x86 的 I/O 結構 學習組合語言的基本工具.
: How many 0's? ★★★☆☆ 題組: Problem Set Archive with Online Judge 題號: 11038: How many 0’s? 解題者:楊鵬宇 解題日期: 2007 年 5 月 15 日 題意:寫下題目給的 m 與 n(m
McGraw-Hill/Irwin © 2003 The McGraw-Hill Companies, Inc.,All Rights Reserved. 肆 資料分析與表達.
朝陽科技大學資管系 李麗華 第四章 鏈結串列 Linked List Fools look to tomorrow, wise men use tonight.
資料結構(計財系).
Activity Networks AOV 網路 AOE 網路. AOV 網路 (Activity on Vertx Networks)  為了表示一件工作中,各子工程間的先後 關係,我們可以利用有向圖中的有向邊代 表事情進行的順序,位於一條有向邊終點 的事件必須要等待起點的事情完成後,才 可以進行。
Presentation transcript:

Data Structure in C ─ 鏈結串列

大綱 單向鏈結串列 環狀串列 雙向鏈結串列 鏈結串列的應用

鏈結串列 以陣列方式存放資料,若要插入(insert)或刪除(delete)某一節點(node)就備感困難 Ex. 陣列中已有a, b, d, e四個元素,若要將c插入d, e需往後一格 Ex.陣列中已有a, b, d, e四個元素,若要將d刪除為不浪費空間需挪移元素 利用鏈結串列(linked list) 解決問題

鏈結串列 (續) 陣列 vs. 鏈結陣列

單向鏈結串列 單向鏈結串列 (single linked list) 若單向串列中的每個節點(node)的資料結構有兩個欄位,分別為資料欄(data)及鏈結欄(next), ,若將節點定義為struct型態,為 struct node{ int data; struct node *next; }; struct node *head=NULL, *tail, *this, *prev, *x, *p, *ptr;

單向鏈結串列 (續) Ex. 串列A={a, b, c, d, e},以鏈結串列表示為 指向串列前端的指標 指向串列尾端的指標

單向鏈結串列 (續) 單向鏈結串列的加入動作 加入於串列的前端 加入於串列的尾端 加入在串列某一特定節點後面

加入於串列的前端 Step 1: x = (struct node *) malloc(sizeof(struct node)); x->next = NULL; Step 2: x->next = head;

加入於串列的尾端 Step 3: head = x; Step 1: x = (struct node *) malloc(sizeof(struct node)); x->next = NULL;

Step 2: tail->next = x; Step 3: tail = x; 若未用tail指標,則每次 都必須要追蹤串列的尾端

加入在串列某一特定節點後面 Assumption: 將一個節點x加在ptr所指節點後面 Step 1: x = (struct node *) malloc(sizeof(struct node)); x->next = NULL; Step 2: x->next = ptr->next;

Step 3: ptr->next = x;

void insert_node(struct node. ptr, struct node. head, struct node void insert_node(struct node *ptr, struct node *head, struct node *tail) { struct node *this if(head == NULL) /* 插入資料為第一筆 */ { ptr->next=NULL; head=ptr; tail=ptr;} else { this=head; if(ptr->key > this->key) /* 插入位置為前端 */ { ptr->next=this; head=ptr; }

else {while(this->next != NULL) { prev=this; this=this->next; if(ptr->key > this->key) /* 插入位置於中間 */ { ptr->next=this; prev->next=ptr; break; } } if(ptr->key <= this->score) /* 插入資料於尾端 */ { ptr->next=NULL; this->next=ptr; tail=ptr; }

單向鏈結串列 (續) 單向鏈結串列的刪除動作 刪除串列前端的節點 刪除串列尾端的節點 刪除串列某一特定節點

刪除串列前端的節點 Step 1: ptr = head; Step 2: head = ptr->next; Step 3: free(ptr);

刪除串列尾端的節點 ptr = head; Step 1:必須先追蹤tail的前一個節點 while (ptr->next != tail) ptr = ptr->next; Step 1:必須先追蹤tail的前一個節點 Step 2: ptr->next = NULL; Step 3: free(tail); Step 4: tail = ptr;

刪除串列某一特定節點 Step 1:尋找所要刪除的節點,並設定兩指標this及prev 即將被刪除的前一節點 即將被刪除節點 while (this->next != NULL) prev = this; this = this->next;

Step 2: prev->next = this->next; Step 3: free(this);

void delete_f(int del_key, struct node *head, struct node *tail) { struct node *clear, *this, *prev; this=head; if(del_key == head->key) { /* 刪除資料於前端 */ clear=this; if(head->next == NULL) /* 資料僅存在一筆 */ tail=NULL; head=head->next; free(clear); } while(this->next != NULL) { /* 刪除資料於中間 */ prev=this; this=this->next; if (del_key == this->key) { prev->next=this->next; free(clear); } } if(del_key == tail->key) { /*刪除資料於尾端 */ prev->next=NULL; tail=prev;

單向鏈結串列 (續) 將兩串列相接 三種情況 x串列為NULL,y串列有資料 x串列有資料,y串列為NULL x串列與y串列都有資料

void concatenate (struct node *x, struct node *y, struct node *y) { struct node *c; if (x = = NULL) z = y; else if (y = = NULL) z = x; else { z=x; c=x; while(c->next != NULL) c = c->next; c->next = y; }

將一串列反轉 串列的反轉是將原先的串列首變成串列尾 Ex. 若一串列原先以小排到大,此時若想由大到小排列 void invert(struct node *head) { struct node *this, *prev, *next_n; next_n = head; this =NULL; while(next_n != NULL){ prev = this; this = next_n; next_n = next->next; this->next = prev; } tail = head; head = this;

單向鏈結串列 (續) 計算串列的長度 串列長度指的是此串列共有多少個節點,計算上只要指標指到的為NULL,則利用一變數做累加,直到指標指到NULL為止 int length(struct node *head) { struct node *this; this = head; int leng=0; while (this != NULL) { leng++’ this = this->next;} return leng; }

環狀串列 假若將鏈結串列最後一個節點的指標指向第一個節點時,此串列稱為環狀串列(circular list) 可以由任一點來追蹤所有節點,而不必區分那一個是第一個節點

環狀串列 (續) 環狀串列的加入動作 加入於串列的前端 加入於串列的尾端 加入在串列某一特定節點後面 若串列為空串列(NULL) 若串列不為空串列 加入於串列的尾端 加入在串列某一特定節點後面

加入於串列的前端 ─ 串列為空串列 加入於串列的前端 ─ 串列不為空串列 Step 1: head = x; tail=x; Step 2: x->next = x; 加入於串列的前端 ─ 串列不為空串列 Step 1: x->next = head;

Step 2: tail->next = x; Step 3: head = x;

加入於串列的尾端 Step 2: x->next = head; Step 1: tail->next = x; Step 3: tail = x;

void insert_node(struct node. ptr, struct node. head, struct node void insert_node(struct node *ptr, struct node *head, struct node *tail) { struct node *prev, *this; if(head == NULL) { /* 插入資料為第一筆 */ ptr->next = ptr; head = ptr; tail = ptr; } else { this = head; if(ptr->key < this->key) { /* 插入位置為前端 */ ptr->next = this; tail->next = head; } else { while(this->next != head) { prev = this; this = this->next;

if(ptr->key < this->key) { /* 插入位置於中間 */ ptr->next = this; prev->next = ptr; break; } } if( ptr->key >= this->key) { /* 插入資料於尾端 */ ptr->next = head; this->next = ptr; tail = ptr; }

環狀串列 (續) 環狀串列的刪除動作 刪除串列前端的節點 刪除串列尾端的節點 刪除串列某一特定節點

刪除串列前端的節點 Step 1: tail->next = head->next; Step 2: ptr=head; head = head->next; Step 3: free(ptr);

刪除串列尾端的節點 ptr = head; Step 1: 必須先追蹤tail的前一個節點 while (ptr->next != tail) ptr = ptr->next; Step 1: 必須先追蹤tail的前一個節點 Step 2: ptr->next = hear; Step 3: free(tail); tail=ptr;

void delete_node(int del_key, struct node *head, struct node *tail) { struct node *clear, *prev, *this; this = head; if(del_key == head->key) { /* 刪除資料於前端 */ clear = head; if(head->next == head) /* 資料僅存在一筆 */ {head = NULL; tail = NULL;} else { head = head->next; tail->next = head; } }

while(this->next != head && head != NULL) /* 刪除資料於中間 */ { prev = this; this = this->next; if(del_key == ,this->key) { clear = this; prev->next = this->next; tail = prev; } } if(del_key == tail->key) { /*刪除資料於尾端 */ clear = tail; prev->next = head; free(clear);

將兩串列相接 Step 1: Atail->next = Bhead; Step 2: Btail->next = Ahead;

雙向鏈結串列 雙向鏈結串列(doubly linked list) 每個節點有三個欄位,一為左鏈結(LLink),二為資料(Data),三為右鏈結(RLink) 特點: 假設ptr是任何節點的指標,則 ptr = ptr->llink->rlink = ptr->rlink->llink; 若此雙向鏈結串列是空串列,則只有一個串列首

雙向鏈結串列 (續) 優點: 缺點: 加入或刪除時,無需知道其前一節點的位址 可以從任一節點找到其前一節點或後一節點 可以將某一節點遺失的左或右指標適時地加以恢復之 缺點: 增加一個指標空間 加入時需改變四個指標(單向只需改變兩個指標) 刪除時需改變兩個指標(單向只要改變一個指標)

雙向鏈結串列 (續) 雙向鏈結串列的加入動作 加入於串列的前端 加入於串列的尾端 加入在串列某一特定節點後面 假設head節點不放任何資料 void init_head(struct node *ptr, struct node *head, struct node *tail) { ptr = (struct node *) malloc (sizeof(struct node)); ptr->key = NULL; ptr->llink = ptr; ptr->rlink = ptr; head = ptr; tail = ptr;} 假設head節點不放任何資料

加入於串列的前端 Step 1: x->rlink = head; Step 2: x->llink = tail; Step 3: tail->rlink = x;

Step 4: head->rlink = x; Step 5: tail = x;

加入於串列的尾端 Assumption: 假設有一串列如下 Step 1: x->rlink = tail->rlink; Step 2: tail->rlink = x;

Step 3: x->llink = tail; Step 4: head->llink = x; Step 5: tail = x;

雙向鏈結串列 (續) 加入在串列某一特定節點後面 必須先搜尋到某特定的節點,並假設此串列是以key由小而大建立的,而搜尋步驟如下: prev = head; ptr = head->rlink; while(ptr != head && x->key <p->key) { prev = ptr; ptr = ptr->rlink; }

void insert_node(struct node. ptr, struct node. head, struct node void insert_node(struct node *ptr, struct node *head, struct node *tail) { struct node *this; this = head->rlink; while(this != head) { if(ptr->key < this->key) { /* 插入位置為中間 */ ptr->rlink = this; ptr->llink = this->llink; this->llink->rlink = ptr; this->llink = ptr; break; } this = this->rlink; } /* 插入位置為尾端 */ if(head->rlink == head || this == head) { ptr->rlink = head; ptr->llink = head->llink; head->llink->rlink = ptr; head->llink = ptr; tail = ptr;} }

雙向鏈結串列 (續) 雙向鏈結串列的刪除動作 刪除串列前端的節點 刪除串列尾端的節點 刪除串列某一特定節點

刪除串列前端的節點 Step 1: ptr = head->rlink; Step 2: head->rlink = ptr->rlink; Step 3: p->rlink->llink = p->llink; Step 4: free(ptr);

刪除串列尾端的節點 Step 1: tail->llink->rlink = head; Step 2: head->llink = tail->llink; Step 3: ptr = tail; Step 4: tail = tail->llink; Step 5: free(ptr);

刪除串列某一特定節點 Assumption: 假設欲刪除this所指的節點 Step 1: this->llink->rlink = this->rlink; Step 2: this->rlink->llink = this->llink; Step 3: free(this);

void delete_node(int del_key, struct node *head, struct node *tail) { struct node *clear, *this; this = head->rlink; while(this != head) { /* 刪除資料於中間 */ if(del_key == this->key) { clear = this; this->llink->rlink = this->rlink; this->rlink->llink = this->llink; if(this == tail) tail = this->llink; break; } this = this->rlink; } free(clear);

鏈結串列的應用 以鏈結串列表示堆疊 以鏈結串列表示佇列 以鏈結串列表示多項式相加

鏈結串列的應用 (續) 以鏈結串列表示堆疊 將堆疊內的資料視為單向鏈結串列中的資料項 Push: 視為將節點加入串列的前端 Pop: 視為刪除前端的節點

鏈結串列的應用 (續) 以鏈結串列表示堆疊 ─ Push void push_stack(int data, struct node *ptr, struct node *top) {ptr = (struct node *) malloc(sizeof(struct node)); ptr->item = data; ptr->next = top; top = ptr; }

鏈結串列的應用 (續) 以鏈結串列表示堆疊 ─ Pop void pop_stack(int data, struct node *top) {struct node *clear if(top ==NULL) printf(“stack-empty”); clear = top; data = top->item; top = top->next; free(clear); }

鏈結串列的應用 (續) 以鏈結串列表示佇列 將佇列內的資料視為單向鏈結串列中的資料項 Enqueue:視為將節點加入串列的尾端 Dequeue:視為刪除前端的節點 由此處開始刪除 由此處開始加入

鏈結串列的應用 (續) 以鏈結串列表示佇列 ─ Enqueue void enqueue(int data, struct node *front, struct node *rear) { ptr = (struct node *) malloc(sizeof(struct node)); ptr->item = data; ptr->next = NULL; if(rear == NULL) front = rear = ptr; else rear->next = ptr; rear = ptr;}

鏈結串列的應用 (續) 以鏈結串列表示佇列 ─ Dequeue void dequeue(int data, struct node *front) {struct node *clear if(front ==NULL) printf(“stack-empty”); data = front->item; clear = front; front = front->next; free(clear); }

鏈結串列的應用 (續) 以鏈結串列表示多項式相加 多項式相加可以用鏈結串列完成,其資料結構為 原理(若有A、B兩多項式) Coef表示變數的係數 Exp表示變數的指數 Link為指下一節點的指標 原理(若有A、B兩多項式) Exp(A) = Exp(B) Exp(A) > Exp(B) Exp(A) < Exp(B)

void poly_add(void) { struct poly *this_n1, *this_n2, *prev; this_n1 = eq_h1; this_n2 = eq_h2; prev = NULL; while(this_n1 != NULL || this_n2 != NULL) /* 當兩個多項式皆相加完畢則結束 */ ptr = (struct poly *) malloc(sizeof(struct poly)); ptr->next = NULL; /* 第一個多項式指數大於第二個多項式 */ if(this_n1 != NULL && (this_n2 == NULL || this_n1->exp > this_n2->exp)) ptr->coef = this_n1->coef; ptr->exp = this_n1->exp; this_n1 = this_n1->next; }

else /* 第一個多項式指數小於第二個多項式 */ if(this_n1 == NULL || this_n1->exp < this_n2->exp) { ptr->coef = this_n2->coef; ptr->exp = this_n2->exp; this_n2 = this_n2->next; } else /* 兩個多項式指數相等,進行相加 */ ptr->coef = this_n1->coef + this_n2->coef; ptr->exp = this_n1->exp; if(this_n1 != NULL) this_n1 = this_n1->next; if(this_n2 != NULL) this_n2 = this_n2->next;

if(ptr->coef != 0) /* 當相加結果不等於0,則放入答案多項式中 */ { if(ans_h == NULL) ans_h = ptr; else prev->next = ptr; prev = ptr; } else free(ptr);