!"#
แผนการสอนประจําบทเรียน รายชือ่ อาจารยผจู ดั ทํา ผศ.รุง ระพี กรานคํายี รายละเอียดของเนือ้ หา ตอนที่ 13.1 การเรียงลําดับแบบควิก (1 คาบ) เรือ่ งที่ 13.1.1
การเรียงลําดับแบบควิก (Quick Sort)
เรือ่ งที่ 13.1.2
ประสิทธิภาพของการเรียงลําดับแบบควิก
เรือ่ งที่ 13.1.3
ตัวอยางโปรแกรมการเรียงลําดับแบบควิก
ตอนที่ 13.2 การเรียงลําดับแบบฮีพ (2 คาบ) เรือ่ งที่ 13.2.1
การเรียงลําดับแบบฮีพ (Heap Sort)
เรือ่ งที่ 13.2.2
ประสิทธิภาพของการเรียงลําดับแบบฮีพ
เรือ่ งที่ 13.2.3
ขั้นตอนการเรียงลําดับขอมูลแบบฮีพ
เรือ่ งที่ 13.2.4
สรุปประสิทธิภาพการเรียงลําดับขอมูลแบบตางๆ
แนวคิด 1. การเรียงลําดับแบบควิก ใชหลักการแบงขอมูลเปนกลุมยอย โดยการคัดเลือกขอมูลมาหนึ่งตัว เปนเกณฑในการแบงเปนสองกลุม ยอย ซึ่งกลุมหนึ่งมีคานอยกวาตัวแบงกลุม อีกกลุมมีคา มากกวาตัวแบงกลุม แลวดําเนินการแบบเดียวกันในแตละกลุม ยอย ลงไปเปนลําดับ จนถึง หนวยยอยสุดของทุกกลุม จะไดขอมูลที่เรียงลําดับ 2. การเรียงลําดับแบบควิก (Quick Sort) ใชวิธีการแบบรีเคอรชัน (Recursion) มาชวยในการ เขียนโปรแกรม ชวยใหสามารถเขียนโปรแกรมไดงาย 3. การเรียงลําดับแบบฮีพ (Heap Sort) ใชแนวคิดจาก โครงสรางขอมูลแบบฮีพ ซึง่ เปนไบนารีท รีแบบพิเศษ คือเปนไบนารีทรีแบบสมบูรณ ซึ่งมีโหนดรากที่มีคามากกวาโหนดลูก มาชวยใน การเรียงลําดับ 4. จากขอดีที่รูปรางของฮีพจะประกันวามีโครงสรางเปนไบนารีทรีที่มีความสูงนอยที่สุด ตาม สมบัติของไบนารีทรีแบบสมบูรณ ทําใหการเปรียบเทียบในแตละรอบไมเกิน O(log2N) เทา นัน้ ซึ่งชวยประกันประสิทธิภาพในการเรียงลําดับขอมูล 5. การเรียงลําดับขอมูลสามารถกระทําไดหลายวิธี แตอาจมีประสิทธิภาพแตกตางกัน
!$% 6. ปจจัยสําคัญที่นํามาพิจารณาประสิทธิภาพของขั้นตอนวิธี ไดแก ฟงชันบิ๊กโอ (function Oh) 7. ปจจัยที่นํามาพิจารณาประกอบอีกอยางหนึ่งคือ ลักษณะของขอมูลเขา ซึ่งมีผลตอเวลาที่ใช ในการทํางานดวย ไดแกกรณี ขอมูลเรียงลําดับอยูแ ลว (Best Case), ขอมูลเรียงสลับลําดับ (Worst Case) และ ขอมูลแบบสุม (Random) วัตถุประสงค หลังจากศึกษาบทเรียนที่ 13 แลว นักศึกษาสามารถ 1. 2. 3. 4.
อธิบายขัน้ ตอนการทํางานของการเรียงลําดับแบบควิกได อธิบายขั้นตอนการทํางานของการเรียงลําดับแบบฮีพได วิเคราะหประสิทธิภาพของขั้นตอนวิธีดวยฟงกชันบิ๊กโอ เปรียบเทียบประสิทธิภาพของขั้นตอนวิธีดวยฟงกชันบิ๊กโอ
กิจกรรมการเรียนการสอน กิจกรรมทีน่ กั ศึกษาตองทําสําหรับการเรียนการสอน ไดแก 1. ศึกษาเอกสารชุดวิชา/โฮมเพจชุดวิชา ตอนที่ 7.1 และตอนที่ 7.2 2. ทํากิจกรรมของบทเรียนที่ 7 3. ทําแบบประเมินผลของบทเรียนที่ 7 เอกสารประกอบการสอน 1. เอกสารชุดวิชา สื่อการสอน 1. โฮมเพจชุดวิชา 2. สไลดประกอบการบรรยาย (Powerpoint) 3. โปรแกรมคอมพิวเตอร ประเมินผล 1. ประเมินผลจากกิจกรรมที่ทํา 2. ประเมินผลจากคําถามทายบทเรียน
!$& ตอนที่ 13.1 การเรียงลําดับแบบควิก หัวเรื่อง เรือ่ งที่ 13.1.1 การเรียงลําดับแบบควิก (Quick Sort) เรือ่ งที่ 13.1.2 ประสิทธิภาพของการเรียงลําดับแบบควิก เรือ่ งที่ 13.1.3 ตัวอยางโปรแกรมการเรียงลําดับแบบควิก แนวคิด 1. การเรียงลําดับแบบควิก เลือกขอมูลหนึง่ ตัวมาเปนเกณฑในการแบงขอมูลออกเปนสองกลุม ยอย โดยกลุมหนึ่งมีคานอยกวาหรือเทากับขอมูลที่ใชเปนตัวแบง กลุมหนึ่งมีคามากกวาหรือ เทากับขอมูลที่ใชเปนตัวแบง 2. นําแตละกลุมยอยมาทําการแบงยอยลงไปอีกดวยวิธีการแบบเดียวกัน จนกระทัง่ แตละกลุม ยอยไมสามารถแบงไดอีก (มีขอมูลเพียงคาเดียว) จึงสิน้ สุด และไดคา ทีเ่ รียงลําดับ 3. สามารถใชเทคนิคแบบรีเคอรชันมาใช ชวยใหเขียนโปรแกรมไดงาย วัตถุประสงค หลังจากที่ศึกษาตอนที่ 13.1 แลว นักศึกษาสามารถ 1. สามารถอธิบายวิธกี ารเรียงลําดับแบบควิกได 2. สามารถประยุกตขน้ั ตอนการเรียงลําดับแบบควิก สําหรับการเรียงลําดับขอมูลทีเ่ ก็บแบบ ระเบียน ใหเรียงตามลําดับของคียที่กําหนดได 3. สามารถพิจารณาถึงประสิทธิภาพของการเรียงลําดับแบบควิกได เรื่องที่ 13.1.1 การเรียงลําดับแบบควิก การเรียงลําดับแบบควิก (Quick Sort) เปนวิธกี ารเรียงลําดับขอมูลที่ใชหลักเกณฑการสลับคา และ จัดวาเปนวิธีที่มีประสิทธิภาพดีที่สุด การทํางานของวิธีนี้จะใชการจัดกลุมขอมูล โดยกําหนดขอมูลตัวหนึ่งเปน ตัวแบงกลุม สมมติใหเปน a[k] เพื่อใหคาขอมูลอยูในรูป a[1] a[2] … a[m]
a[m+1] a[m+2] … a[N]
โดยที่
a[1] a[2] … a[m]
<= a[k]
และ
a[m+1] a[m+2] … a[N] >= a[k]
!$! เมื่อจัดกลุมขอมูลไดดังรูปแลว ขอมูลในแตละกลุมก็จะนําไปจัดกลุมก็จะนําไปจัดกลุมดวยวิธีการ แบบเดิมอีก และกระทําไปจนกระทั่งไมสามารถแบงกลุมยอยไดอีก ก็จะสิน้ สุดการทํางาน ซึ่งเปนทํางานแบบรี เคอรชนั การกําหนดขอมูลที่เปนตัวแบงกลุม หรือ a[k] อาจทําไดหลายวิธี เชน ใชขอมูลตัวแรกของกลุมมา เป น ตั ว แบ ง ใช ตั ว กลางเป น ตั ว แบ ง หรื อ เลื อ กตั ว หนึ่ ง ตั ว ใดก็ ไ ด ในที่ นี้ ใ ช ตั ว กลางคื อ k = (l+r) / 2 เมื่อ l : ตําแหนงสมาชิกตัวแรก และ r : ตําแหนงสมาชิกตัวสุดทาย วิธีการจัดกลุมใชการคนสมาชิกทางซายของ a[k] ซึ่งมีคามากกวา a[k] และสมาชิกทางขวาของ a[k] ที่มีคานอยกวา a[k] แลวนํามาสลับทีก่ นั ดังนี้
i
j
l
r
a[1]
a[k] a[i]>a[k]
a[n] a[i]<a[k]
สลับคา
สลับคา a[i] a[ j ] เมื่อพบ a[i] > a[k] และ a[ j ] < a[k] และหยุดการทํางานเมื่อ i > j ผลการ จัดกลุมจะไดขอมูล 2 กลุม ดังนี้
l
j
ขอมูล <= a[k]
i ขอมูล => a[k]
ถา j > l ใหนําขอมูล a[ l ]…a[ j ] ไปจัดเรียงดวยวิธีเดิม ถา i < r ใหนําขอมูล a[ i ]…a[ r ] ไปจัดเรียงดวยวิธีเดิม
r
!$" ชัน้ ตอนการทํางานของการเรียงลําดับแบบควิก แสดงดวยโปรซิเจอร QuickSort ดังรูป 13.2 Procedure QuickSort (Var a : List ; Lo,Hi : Integer); {…………………….sort………………….} procedure sort ( l , r : Integer) ; Var i , j , k : Integer ; x , y : Dataitem ; Begin i := l ; j := r ; k := (l + r) DIV 2 ; x := a[k] ; Repeat While a[i] < x Do i := i + 1 ; While a[i] < x Do j := j - 1 ; If i <= j Then Begin y := a[ i ] ; a[ i ] := a[ j ] ; a[ j ] := y ; i := i + 1 ; j := j – 1 End Until i > j ; If i < j Then sort (l , j) ; If i < r Then sort (i , r) End ; {sort} {………………………………..} Begin {quicksort} sort (Lo,Hi) End ;
โปรแกรม 13.1 การเรียงลําดับแบบควิก กิจกรรมที่ 13.1 ทดลองการเรียงลําดับแบบควิก ทดลองเรียงลําดับขอมูลแบบควิกตามขั้นตอนการทํางานในรูป 13.2 จากขอมูลตัวอยางตอไปนี้ (ก) 15
33 26 69 89 61
(ข)
15 26 33 61 69 89
(ค)
89 69
61 33 26 15
กิจกรรมที่ 13.2 หาประสิทธิภาพการเรียงลําดับ สังเกตผลการเรียงลําดับจากกิจกรรมที่ 13.1 สิทธิภาพในการเรียงลําดับหรือไม อยางไร
ทานคิดวาลักษณะลําดับของขอมูลเขามีผลตอประ
!$$ เรื่องที่ 13.1.2 ประสิทธิภาพของการเรียงลําดับแบบควิก พิจารณาจํานวนครั้งของการเปรียบเทียบ = N+2(N/2)+4(N/4)+8(N/8)+…+N(N/N) ซึ่งมี log2 N เทอม ดังนัน้ จํานวนครัง้ การเปรียบเทียบเทากับ N(log2N) หรือมีประสิทธิภาพเปน 0(N log2N) การเลือกตัวแบงกลุมจากตัวอยางขางตนใชตัวกลางของกลุมขอมูล ซึ่งอาจใชวิธีอื่นๆในการเลือกตัว แบงกลุมก็ได ในบางตัวอยางอาจเลือกจากขอมูลตัวแรกของกลุม ในวิธีนี้อาจมีผลใหประสิทธิภาพการทํางาน เปลี่ยนแปลงไปตามลักษณะของขอมูลเขา โดยเฉพาะเมื่อขอมูลเขาเรียงลําดับอยูแลวทําใหแทนที่จะแบงกลุม ใหเปนสองสวนทีม่ ขี นาดใกลเคียงกัน กลับทําใหแบงเปนกลุมฝงเดียวซึ่งมีคามากกวาตัวแบงกลุม ในลักษณะ นีจ้ ะไดประสิทธิภาพการทํางานเปน O(N2) ตารางตอไปนี้แสดงเวลาที่ใชในการเรียงลําดับขอมูล เพื่อเปรียบเทียบประสิทธิภาพการเรียงลําดับ แตละแบบ เมื่อจํานวนขอมูลเพิ่มขึ้น และเมื่อขอมูลเขามีลักษณะแตกตางกัน ตาราง 13.1 เปรียบเทียบเวลาการเรียงลําดับขอมูลแบบตางๆ จํานวนขอมูล = 256 การเรียงลําดับ
ลักษณะเขามูลนําเขา เรียงลําดับแลว
สุม
เรียงสลับลําดับ
แบบฟอง
1.26
2.04
2.80
แบบแทรก
0.20
0.82
1.64
แบบคัดเลือก
0.94
0.96
1.18
แบบควิก
0.08
0.12
0.08
จํานวนขอมูล = 2048 การเรียงลําดับ แบบฟอง
ลักษณะขอมูลเขา เรียงลําดับแลว
สุม
เรียงสลับลําดับ
80.18
128.84
178.66
แบบแทรก
0.22
50.74
103.80
แบบคัดเลือก
58.18
58.34
73.46
0.72
1.22
0.76
แบบควิก
!$' เรื่องที่ 13.1.3 ตัวอยางโปรแกรม ตัวอยาง 13.1 โปรแกรม Quick Sort Demo โปรแกรม Quick_Sort_Demo แสดงการเรียงลําดับแบบควิก โปรแกรมนี้สรางขอมูลทดสอบโดยใช ฟงกชนั เลขสุม สรางเลขจํานวนเต็มซึ่งมีคาระหวาง 0 ถึง 100 และใหผูใชระบุจํานวนขอมูลทดสอบ แสดงขอ มูลทดสอบและผลการเรียงลําดับบนจอภาพ Program Quick_Sort_Demo ; {$R-,S-} Uses Crt ; { This program. demonstrates the quicksort algorithm, which } { provides. an extremely efficient method of sorting arrays in } { memory. The program generates a list of random numbers } { between 0 and 100, and then sorts them using the QUICKSORT } { procedure. Finally, the sorted list is output on the screen. } { Note that stack and range checks are turn off (through the } { compiler directive above) to optimize execution speed. } Const Max = 1,000 ; Type
DataItem = Integer ; List = Array[1..Max] of DataItem ; Var data : List ; i ,num : Integer; ch : Char ; {……………………………………………………………..} Procedure Quicksort (Var a:List; Lo, Hi : Integer) ; Procedure Sort (l,r : Integer) ; Var i , j : Integer ; x,y : DataItem ; Begin i := l , j := r ; x := a[(l+r) DIV 2] ; Repeat While a[i] < x Do i := i + 1 ; While x < a[ j ] Do j := j -1 ; If i <= j Then Begin y := a[i] ; a[i] := a[ j ] ; a[ j ] := y ; i := i + 1 ; j := j – 1 End ; Until i>j ; If l < j Then Sort (l , j) ; If i < r Then Sort (i , r) ; End ; {Sort} Begin
!$( Sort (Lo , Hi) ; End ; {Quicksort} {--------------------------------------------------------------------------} Begin {Main} Clrscr ; Writeln( ‘*** QUICK SORT ***’ : 40) ; Writeln ; Write (‘Enter number of test data : ’ ) ; ReadIn (num) ; Writeln ; Writeln( ‘Generating ‘,num,’ random numbers…’ ) ; Writeln ; Randomize ; For i := 1 to num Do Begin Data[i] := Random(100) ; Write(data[i] : 5) End ; Writeln ; Writeln( ‘Sorting random numbers…’ ) ; Quicksort (data, 1, num) ; Writeln ; For i := 1 to num Do Write (data[i]) ; Writeln ; Writeln ; Writeln( ‘Press Any Key…’) ; ch := Readkey Writeln End.
โปรแกรม 13.2 โปรแกรม Quick_Sort_Demo ตัวอยางการทํางานของโปรแกรม Quick_Sort_Demo *** QUICK SORT ***
Enter number of test data : 15 Gerating 15 random numbers… 89 33 89 69 26 61 79 75 Sorting random numbers… 14 15 26 33 43 49 97 99 Press Any Key…_
43
99
49
89
15
97
14
61
69
75
79
89
89
89
!$) กิจกรรมที่ 13.3
ทดสอบโปรแกรมตัวอยางที่ 13.1
ทดสอบโปรแกรมตัวอยางที่ 13.1 โดยลองเปลีย่ นจํานวนขอมูลเปน 30, 50, และ 100 คา ตัวอยาง 13.2 โปรแกรม Phone Sort โปรแกรม Phone_sort เปนตัวอยางสําหรับเรียงสําหรับเรียงลําดับขอมูลในแฟมสุม (Random File) โดยใชการเรียงลําดับแบบควิก การอางอิงถึงขอมูลแตละรายการใชหมายเลขระเบียนในปาสกาลเริ่มตั้ง แต 0, 1, 2,..., n ดังนัน้ จึงดูเสมือนเปนการเรียงลําดับขอมูลแบบแถวลําดับในจานบันทึก ขอมูลแตละระเบียน ในแฟมขอมูลประกอบดวย ชื่อ และ หมายเลขโทรศัพท โปรแกรมนี้จะเรียงลําดับขอมูลในแฟมชื่อ Phone.Dat ซึ่งบันทึกขอมูลไวแลวอยูในจานบันทึก โดย เรียงลําดับขอมูลตามอักขระของชื่อ และผลการเรียงลําดับบันทึกกลับลงบนแฟมเดิม ซึ่งจะเห็นวาขั้นตอนวิธี ยังคงเปนแบบเดิม เพียงแตปรับปรุงคําสั่งสําหรับอางอิงขอมูลในแฟมเล็กนอยเทานั้น Program Phonesort ; Uses Crt ; Type Phone_rec =
Record Name : String [15] ; Phone : String [15]
End ; Str15 = String [15]; Dataitem = Phone_rec ; Datafi = File of Dataitem ; Var P : Dataitem ; Fi : Datafi ; n : integer ; Function Find (Var fb : Datafi ; i : Integer) : Str15 ; Var t : Dataitem Begin i := i – 1 ; {record number begin with 0} Seek (fp , i) ; Read (fp , t) ; Find := t.name {return name of i th person} End ; {Find} Procedure Qsrand (Var fp :Datafi ; count : Integer) ; {---- Recursive Quick Sort ----} Procedure Qs (I , r : Integer) ; Var i, j, k : Integer ; x, y, z : Dataitem ; Begin i := I ; j := r ; k := (I+r) DIV 2 ; Seek (fp, k –1) ; Read (fp, x) ; {get a record} Repeat
!$* While find (fp,i) < x.name Do i := i + 1 ; While find (fp,j) > x.name Do j := j - 1 ; If i < j Then Begin {swap records on disk} Seek (fp, i – 1) ; Read ( fp, y); Seek (fp, j – 1) ; Read ( fp, z); Seek (fp, j – 1) ; Write ( fp, y); Seek (fp, i – 1) ; Write ( fp, z); i := i + 1 ; j = j – 1 ; End ; Until i > j ; If I < j Then Qs (I , j) ; If i < r Then Qs (i , r) End; {Qs} Begin Qs ( 1 , count ) ; End ; {Qsrand} Begin {main} Clrscr ; WriteIn( ‘ *** SORT DATA RECORD IN RANDOM FILE *** ’ ) ; Assign (fi ,’Phone.dat’) ; Reset (fi) ; n := Filesize (fi) ; WriteIn ; WriteIn( ‘Please wait for file sorting’) ; Qsrand (fi,n) ; Ciose (fi) ; WriteIn(‘Now, file is sorted already’) ; WriteIn( ‘ *** List data from file *** ‘); Reset(fi) ; While Not Eof (fi) Do Begin Read( fi , p) ; WriteIn (p.name : 15 , p.phone : 20 ); End ; close(fi) ; End.
โปรแกรม 13.3 โปรแกรม Phone Sort กิจกรรมที่ 13.4
ทดสอบโปรแกรมตัวอยาง 13.2
ทดสอบโปรแกรมตัวอยาง 13.2 โดยในเบื้องตนตองเขียนโปรแกรมเพื่อสรางแฟม Phone.dat เพื่อเก็บขอมูลชื่อและหมายเลขโทรศัพท ใหมีโครงสรางระเบียนตามที่กําหนดกอน แลวนํามาทดสอบและดู ผลการเรียงลําดับขอมูล หมายเหตุ ใหสรางขอมูลทดสอบไมต่ํากวา 20 ระเบียน
!$# ตอนที่ 13.2
การเรียงลําดับแบบฮีพ
หัวเรื่อง เรือ่ งที่ 13.2.1 การเรียงลําดับแบบฮีพ (Heap Sort) เรือ่ งที่ 13.2.2 ประสิทธิภาพของการเรียงลําดับแบบฮีพ แนวคิด 1. การเรียงลําดับแบบฮีพ เปนการนําสมบัติของโครงสรางแบบฮีพ ซึง่ เปนไบนารีทรีแบบพิเศษ และเปนไบนารีทรีแบบสมบูรณ มาชวยในการเรียงลําดับขอมูล 2. โหนดรากของฮีพ จะเก็บคาสูงสุดของขอมูลในฮีพเสมอ จึงใชวิธีถอดโหนดรากของฮีพมาตาม ลําดับ ก็จะไดชุดขอมูลที่เรียงลําดับตามตองการ 3. การถอดรากของฮีพมาแตละครัง้ ตองทําการจัดโครงสรางขอมูลใหม ใหคงสมบัติของฮีพ 4. เนื่องจากฮีพเปน เปนไบนารีทรีแบบสมบูรณ จึงมีจํานวนการสลับคาขอมูลในการปรับฮีพแตละ ครัง้ ไมเกิน log2 N ซึ่งชวยประกันประสิทธิภาพการทํางานของการเรียงลําดับแบบฮีพ วัตถุประสงค หลังจากที่ศึกษาตอนที่ 13.2 แลว นักศึกษาสามารถ 1. สามารถอธิบายวิธีการเรียงลําดับแบบฮีพได 2. สามารถพิจารณาถึงประสิทธิภาพของการเรียงลําดับแบบฮีพได เรื่องที่ 13.2.1 การเรียงลําดับแบบฮีพ (Heap Sort) โครงสรางขอมูลแบบฮีพ (Heap) เปนโครงสรางขอมูลแบบพิเศษของไบนารีทรีที่มีสมบัติเปนไบ นารีทรีแบบสมบูรณ (Complete Binary Tree) ซึ่งคาของโหนดรากจะมากกวาหรือเทากับคาของโหนดลูก เสมอ ดังนัน้ พิจารณาลักษณะของฮีพ จะเห็นวา • ทุกระดับของฮีพจะแตกสาขาออกไปได 2 ทางคือทางซายและทางขวา และตองเปนไบนารีทรี แบบสมบูรณ คือตองมีโหนดในระดับบนครบ 2 ดานกอน จึงจะแตกโหนดระดับลางได • การแตกโหนดตองแตกโหนดดานซายกอนแลวจึงแตกดานขวา • คาของโหนดพอ ตองสูงกวาหรือเทากับโหนดลูก พิจารณารูปตัวอยางของฮีพ
!'%
รูป (ก) ขอมูลในโครงสรางแบบฮีพ
รูป (ข) แทนโครงสรางแบบฮีพดวย Array
รูป 13.3 การแทนขอมูลในโครงสรางแบบฮีพ
กิจกรรมที่ 13.5 จากรูปตอไปนี้ พิจารณาวารูปใดไมใชฮีพ
(ก)
(ข)
(ค)
กิจกรรมที่ 13.6 แทนรูปฮีพในกิจกรรมที่ 13.5 ดวย array ในโครงสรางแบบฮีพ คาขอมูลสูงสุดเก็บที่โหนดรากของฮีพเสมอ เราจึงสามารถนําสมบัตดิ งั กลาว มาชวยในการเรียงลําดับขอมูล โดยใชวิธีการดังนี้
!'& 1. ถอดโหนดราก (คาสูงสุด) ออกจากฮีพ นําไปวางลงในที่เก็บขอมูลตามลําดับคา 2. ปรับโครงสรางฮีพใหม 3. ทําซ้ําจากขั้นตอนที่ 1 จนหมดสมาชิกในฮีพ การเรียงลําดับดวยวิธนี ้ี จะคลายกับวิธี Selection Sort ในแงที่เลือกหยิบคามากที่สุดหรือนอยที่ สุดจากชุดขอมูลทีเ่ หลืออยูม าวางเรียงกันเปนลําดับ แตการเปรียบเทียบในการปรับโครงสรางของฮีพ ซึง่ ประกันวา เปนไบนารีทรีที่มีความสูงนอยที่สุดแตละครั้งจะไมเกิน O(log2N) จึงใชเวลานอยกวา Selection Sort ซึง่ ตองทําการเปรียบเทียบในแตละรอบเปน O(N) การจัดเรียงขอมูลในฮีพ จะดําเนินการโดย 4. สลับคาของโหนดรากซึง่ เปนคาสูงสุด กับคาในโหนดสุดทายของฮีพ (ถือวาโหนดสุดทายนี้ ไมอยูในฮีพแลว) 5. ปรับโครงสรางของฮีพใหมใหถูกตอง 6. ดําเนินการซ้าํ จนกระทั่งหมดขอมูลในฮีพ
ขอมูลเริม่ ตนของฮีพ 1. สลับคาโหนดราก คือ 100 กับคาโหนดสุดทายคือ 7
ปรับฮีพ
2. สลับ 36 กับ 2
ปรับฮีพ
!'! 3. สลับ 25 กับ 1
ปรับฮีพ
4. สลับ 19 กับ 2
ปรับฮีพ
5. สลับ 17 กับ 2
ปรับฮีพ
6. สลับ 7 กับ 1
ปรับฮีพ
7. สลับ 3 กับ 2
!'"
ปรับฮีพ
8. สลับ 2 กับ 1
เหลือโหนดเดียวไมตองปรับฮีพ
สิน้ สุดการทํางาน ขอมูลเรียงลําดับแลว
ภาพประกอบ 13.1 การเรียงลําดับแบบฮีพ เราสามารถแทนโครงสรางของฮีพดวย Array ดังตัวอยางในรูป 13.3 (ข) วิธีการเรียงลําดับแบบฮีพ โดยแทนฮีพดวย Array แสดงในรูป 13. 5
ฮีพเริ่มตน 1. สลับ 100 กับ 7 ปรับฮีพ 2. สลับ 36 กับ 2
[1]
[2]
[3]
[4]
[5]
[6]
[7]
[8]
[9]
100
19
36
17
3
25
1
2
7
7
19
36
17
3
25
1
2
100
36
19
25
17
3
7
1
2
100
2
19
25
17
3
7
1
36
100
!'$ ปรับฮีพ 3. สลับ 25 กับ 1 ปรับฮีพ 4. สลับ 19 กับ 2 ปรับฮีพ 5. สลับ 17 กับ 2 ปรับฮีพ 6. สลับ 7 กับ 1 ปรับฮีพ 7. สลับ 3 กับ 2 ปรับฮีพ 8. สลับ 2 กับ 1 ปรับฮีพ สิน้ สุดการเรียงลําดับ
25
19
7
17
3
2
1
36
100
1
19
7
17
3
2
25
36
100
19
17
7
1
3
2
25
36
100
2
17
7
1
3
19
25
36
100
17
3
7
1
2
19
25
36
100
2
3
7
1
17
19
25
36
100
7
3
2
1
17
19
25
36
100
1
3
2
7
17
19
25
36
100
3
1
2
7
17
19
25
36
100
2
1
3
7
17
19
25
36
100
2
1
3
7
17
19
25
36
100
1
2
3
7
17
19
25
36
100
1
2
3
7
17
19
25
36
100
1
2
3
7
17
19
25
36
100
ภาพประกอบ 13.2 การเรียงลําดับแบบฮีพโดยใช Array กิจกรรมที่ 13.7 เรียงลําดับขอมูลที่อยูในฮีพตอไปนี้
กิจกรรมที่ 13.8 เรียงลําดับขอมูลจากฮีพของกิจกรรมที่ 13.7 โดยแทนฮีพดวย array
!'' เรื่องที่ 13.2.2 ประสิทธิภาพของการเรียงลําดับแบบฮีพ ประสิทธิภาพการทํางานของการเรียงลําดับขอมูลแบบฮีพ จะไมมีประสิทธิภาพมากนัก เมื่อมีขอมูล ปริมาณนอย แตถาหากมีขอมูลปริมาณมากวิธีการนี้นับวาเปนวิธีที่มีประสิทธิภาพดี พิจารณาขัน้ ตอนการทํางาน • ประกอบดวยการทํางานวนซ้าํ N-1 รอบ ในแตละรอบมีการสลับที่ และปรับฮีพ • การสลับที่ แตละรอบกระทําเพียง 1 ครัง้ O(1) • การปรับฮีพ จากการที่ตองถอดคาของโหนดรากลงมา และจัดลําดับคาคียของฮีพใหม โครง สรางของฮีพที่มี N โหนด มีจํานวนระดับเทากับ log2 (N + 1) ดังนั้นจํานวนครั้งที่ตองมีการ สลับคาของขอมูลในการปรับฮีพแตละรอบ ไมเกิน log2 N ดังนั้นในการปรับฮีพมีคาบิ๊กโอเปน O(log2 N) ดังนัน้ เมือ่ คูณกับจํานวนรอบการทํางานทัง้ สิน้ N-1 รอบ ซึง่ เปน O(N) จะไดจํานวนการทํางานซ้ํา เปน O(N log2 N) เรื่องที่ 13.2.3 ขั้นตอนการเรียงลําดับขอมูลแบบฮีพ ขั้นตอนการทํางานของโปรแกรมเรียงลําดับขอมูลแบบฮีพ เริ่มจากขอมูลเขาอยูใน Array ขอมูลจะ ถูกดําเนินการทีละตัวจากโหนดรากของฮีพ (ขอมูลตัวแรกใน Array) ขอมูลในสวนของฮีพจะลดลงทีละตัวใน แตละรอบ โดยนําไปวางในสวนขอมูลที่จัดเรียงลําดับแลว จนกระทั่งหมดขอมูลในฮีพ ก็สน้ิ สุดการทํางาน ในแตละครั้งที่มีการนําโหนดรากของฮีพออกไป ตองมีการปรับโครงสรางของฮีพใหม (Reheap) (พิจารณารูปตัวอยาง 13.4 และ 13.5 ) ไดแกการนําโหนดลูกทีม่ คี า สูงสุดมาเปนรากแทน เพื่อใหคงสมบัติ ของฮีพ สมมติแทนฮีพดวย array ดังนี้ Const MaxElements Type ArrayType
= 100; =
(*
Maximum possible number of elements *)
Array [1 .. MaxElements] of
ขั้นตอนการปรับฮีพคือ Procedure ReheapDown เปนดังนี้ ReheapDown (HeapElements, Root, Bottom) (* At the start, Root is the index of the node that *) (* (possibly) violates the heap order property. *)
ElementType;
!'( HeapOK ! False While Root node is not a leaf AND NOT HeapOK Calculate MaxChild (the index of the child of the current root node with the larger value) If value of Root node < value of MaxChild node Then Swap value of Root node and MaxChild node Root ! MaxChild Else HeapOK ! True End (* While *)
พารามิเตอร HeapElement คือขอมูลในฮีพ ซึ่งแทนดวย array Root คือดัชนีของ array ที่ชี้โหนดรากของ ฮีพ และ Bottom เปนดัชนีของ array ที่ชี้โหนดทายสุดของฮีพ การหาคา MaxChild ทําไดโดยตรวจสอบวา โหนดรากเปนรากที่มีลูกเพียงหนึ่งโหนดหรือไม ถาใช ก็จะเปนลูกทางฝง ซาย ตามสมบัติของตนไมสมบูรณ มิฉะนั้นตองเปรียบเทียบคาของโหนดลูกทางซายและ ขวา เพื่อหาโหนดที่มีคามากกวา เขียนเปนโปรซิเจอรไดดงั โปรแกรม
!') Procedure
ReHeapDown (Var HeapElements : ArrayType ; Root, Bottom :Integer) ; (* Restores the order property of heaps to the subtree starting at the Root *) (* It is assumed that, on invocation of the procedure, the order property is *) (* violated only by the root node *) Var HeapOK : Boolean; (* The heap repair is finished. *) MaxChild : Integer; (* index of the larger child value *) Begin (* ReheapDown *) HeapOK := False; (* Process until Root value is in its correct place. *) While (Root * 2 <= Bottom) AND NOT HeapOK Do Begin (* Calculate index of the child with the larger value. *) If Root * 2 = Bottom Then (* There is onlyone child node. *) MaxChild := Root * 2 Else (* pick the greater of the two children *) If HeapElements[Root * 2] > (* left child *) HeapElements[Root * 2 + 1] (* right child *) Then MaxChild := Root * 2 Else MaxChild := Root * 2 + 1; (* If the heap property is violated, Swap values *) If HeapElements [Root] < HeapElements [MaxChild] Then Begin (* not yet a heap *) Swap ( HeapElements [Root], HeapElements [MaxChild] ); Root := MaxChild End (* if not a heap *) Else (* already is a heap *) HeapOK := True End (* while *) End; (* ReheapDown *)
โปรแกรม 13.4 โปรแกรมสําหรับทําการปรับฮีพ
การเรียงลําดับขอมูลแบบฮีพใน array จะประกอบดวยการสลับคาโหนดรากกับโหนดสุดทายของฮีพ แลวปรับฮีพ และวนรอบจนหมดขอมูล ซึง่ สามารถเขียนเปนโปรซิเจอรไดดงั โปรแกรม
!'* Procedure HeapSort (Var Data
: ArrayType; NumElements : Integer ); (* Sort the first NumElements values of array Data in ascending order, *) (* using the heapsort algorithm . *) Var NodeIndex : Integer; Begin (* HeapSort *) (* Sort the elements in the heap by swapping the root *) (* (current largest) value with the last unsorted value *) (* then reheaping the remaining part of the array . *) For NodeIndex := NumElements Downto 2 Do Begin Swap (Data [1] , Data [NodeIndex] ); ReheapDown (Data, 1, NodeIndex – 1) End (* For loop *) End; (* HeapSort *)
โปรแกรม 13.5 โปรซิเจอรสาํ หรับทําการเรียงลําดับขอมูลแบบฮีพ จากการเรียงลําดับแบบฮีพในวิธีขางตน เปนการเรียงลําดับโดยที่สมมติใหขอมูลที่เขามาเก็บใน โครงสรางแบบฮีพอยูแลว ถาขอมูลเขาไมไดมีโครงสรางแบบฮีพ ตองเพิ่มขั้นตอนในการจัดโครงสรางของ ฮีพไวกอนเริ่มเรียงลําดับขอมูล กิจกรรมที่ 13.9 เขียนและทดสอบโปรแกรมเพื่อทําการเรียงลําดับขอมูลแบบฮีพ ใหเขียนและทดสอบโปรแกรมเพื่อทําการเรียงลําดับขอมูลแบบฮีพ โดยใชขั้นตอนวิธีจากโปรซิเจอร HeapSort และ ReheapDown โดยใหอานขอมูลของฮีพเขาทางแปนพิมพ และแสดงผลการเรียงลําดับขอมูล บนจอภาพ ตามลําดับการทํางานแตละรอบจนสิน้ สุดการทํางาน เรื่องที่ 13.2.4 สรุปประสิทธิภาพการเรียงลําดับขอมูลแบบตางๆ • การเรียงลําดับขอมูลสามารถกระทําไดหลายวิธี เชนเดียวกับขั้นตอนวิธีในการแกปญหาอื่นๆ ดวยโปรแกรมคอมพิวเตอร การใชขั้นตอนวิธีที่แตกตางกันสามารถใหผลการทํางานเชนเดียว กัน แตอาจมีประสิทธิภาพแตกตางกัน • ปจจัยสําคัญที่นํามาพิจารณาประสิทธิภาพของขั้นตอนวิธี ไดแก เวลาทีใ่ ชในการดําเนินการ เมื่อปริมาณขอมูลมากขึ้น แสดงในรูปของฟงชันบิ๊กโอ (function Oh) การพิจารณาดวย ฟงชัน บิ๊กโอเปนวิธีที่ทําไดงายและเห็นไดชัดเจน สามารถนํามาชวยเปรียบเทียบประสิทธิภาพของขั้น ตอนวิธีไดโดย’งาย ไมตองใชเครื่องมือหรืออุปกรณใดๆ
!'# • ปจจัยที่นํามาพิจารณาประกอบอีกอยางหนึ่งคือ ลักษณะของขอมูลเขา ซึ่งมีผลตอเวลาที่ใชใน การทํางานดวย ไดแกกรณี ขอมูลเรียงลําดับอยูแ ลว (Best Case), ขอมูลเรียงสลับลําดับ (Worst Case) และ ขอมูลแบบสุม (Random) จากวิธีการเรียงลําดับขอมูลแบบตางที่ไดกลาวถึง ทํางานไดดงั ตาราง 13-2
สามารถเปรียบเทียบสรุปประสิทธิภาพการ
ตาราง 13.2 สรุปประสิทธิภาพการเรียงลําดับขอมูลแบบตางๆ
วิธเี รียงลําดับ
เรียงลําดับ
ลักษณะขอมูลเขา แบบสุม
Selection
O(N2)
O(N2)
O(N2)
Bubble
O(N2)
O(N2)
O(N2)
Insertion
O(N)
O(N2)
O(N2)
MergeSort
O(N log N)
O(N log N)
O(N log N)
Quick Sort
O(N log N)
O(N log N)
O(N2) ใชคาแรกเปนตัวแบง
HeapSort
O(N log N)
O(N log N)
O(N log N)
เรียงสลับลําดับ
ตาราง 13.3 ตัวอยางคาของฟงกชันแบบตางๆ ตามคาของ N N
Log2N
N2
N Log2N
N3
2N
1
0
0
1
1
2
2
1
2
4
8
4
4
2
8
16
64
16
8
3
24
64
512
256
16
4
64
256
4,096
65,536
32
5
160
1,024
64
6
384
4,096
262,144
……..
128
7
896
16,384
2,096,152
……..
256
8
2,048
65,536
16,777,216
……..
32,768 2,147,483,648
!(%