Tải bản đầy đủ (.docx) (14 trang)

MÔ PHỎNG THUẬT TOÁN HEAPSORT & QUICK SORT TRÊN MAPLE

Bạn đang xem bản rút gọn của tài liệu. Xem và tải ngay bản đầy đủ của tài liệu tại đây (1.34 MB, 14 trang )

ĐẠI HỌC QUỐC GIA THÀNH PHỐ HỒ CHÍ MINH
CHƯƠNG TRÌNH ĐÀO TẠO THẠC SĨ CNTT
Tiểu luận : MÔ PHỎNG THUẬT TOÁN
HEAPSORT & QUICK SORT TRÊN
MAPLE
TP.HCM 01/01/2013
Giảng viên hướng dẫn : PGS.TS Đỗ Văn Nhơn
Học viên thực hiện : Đoàn Vũ Ngọc Duy
MSSV : CH1101010
2
I. Thuật toán Heapsort
1. Mô tả bài toán
Mỗi mảng a[1 n] có thể xem như một cây nhị phân gần đầy (có trọng số là các
giá trị của mảng), với gốc ở phần tử thứ nhất, con bên trái của đỉnh a[i] là a[2*i]
con bên phải là a[2*i+1] (nếu mảng bắt đầu từ 1 còn nếu mảng bắt đầu từ 0 thì 2
con là a[2*i+1] và a[2*i+2] ) (nếu 2*i<=n hoặc 2*i+1<=n, khi đó các phần tử có
chỉ số lớn hơn không có con, do đó là lá).
Ví dụ mảng (45,23,35,13,15,12,15,7,9) là một đống
Một cây nhị phân, được gọi là đống cực đại nếu khóa của mọi nút không nhỏ hơn
khóa các con của nó. Khi biểu diễn một mảng a[] bởi một cây nhi phân theo thứ
tự tự nhiên điều đó nghĩa là a[i]>=a[2*i] và a[i]>=a[2*i+1] với mọi i =1 int(n/2).
Ta cũng sẽ gọi mảng như vậy là đống. Như vậy trong đống a[1] (ứng với gốc của
cây) là phần tử lớn nhất. Mảng bất kỳ chỉ có một phần tử luôn luôn là một đống.
Một đống cực tiểu được định nghĩa theo các bất đẳng thức ngược lại:
a[i]<=a[2*i] và a[i]<=a[2*i+1]. Phần tử đứng ở gốc cây cực tiểu là phần tử nhỏ
nhất.
Vun đống
Việc sắp xếp lại các phần tử của một mảng ban đầu sao cho nó trở thành đống
được gọi là vun đống.
Vun đống thứ i
Nếu hai cây con gốc 2 * i và 2 * i + 1 đã là đống thì để cây con gốc i trở thành


đống chỉ việc so sánh giá trị a[i] với giá trị lớn hơn trong hai giá trị a[2 * i] và a[2
* i + 1], nếu a[i] nhỏ hơn thì đổi chỗ chúng cho nhau. Nếu đổi chỗ cho a[2 * i],
3
tiếp tục so sánh với con lớn hơn trong hai con của nó cho đên khi hoặc gặp đỉnh
lá. (Thủ tục DownHeap trong giả mã dưới đây)
Vun một mảng thành đống
Để vun mảng a[1 n] thành đống ta vun từ dưới lên, bắt đầu từ phần tử a[j]với j
=Int(n/2) ngược lên tới a[1]. (Thủ tục MakeHeap trong giả mã dưới đây) kho qua
Sắp xếp bằng vun đống
Đổi chỗ (Swap): Sau khi mảng a[1 n] đã là đống, lấy phần tử a[1] trên đỉnh của
đống ra khỏi đống đặt vào vị trí cuối cùng n, và chuyển phần tử thứ cuối cùng
a[n] lên đỉnh đống thì phần tử a[n] đã được đứng đúng vị trí.
Vun lại
Phần còn lại của mảng a[1 n-1] chỉ khác cấu trúc đống ở phần tử a[1]. Vun lại
mảng này thành đống với n-1 phần tử.
Lặp
Tiếp tục với mảng a[1 n-1]. Quá trình dừng lại khi đống chỉ còn lại một phần tử
2. Thuật giải
Giai đoạn 1: Hiệu chỉnh dãy số ban đầu thành Heap
Giai đoạn 2: Sắp xếp dãy số dựa trên Heap
Bước 1 : Đưa phần tử lớn nhất về vị trí đứng ở cuối dãy
r = n;
Hoán vị (a1,ar)
Bước 2: Loại bỏ phần tử lớn nhất ra khỏi Heap r = r - 1;
4
Hiệu chỉnh phần còn lại của dãy từ al đến ar thành một Heap.
Bước 3 : Nếu r >1 ( heap còn phần tử) : lặp lại bước 2
Ngược lại : dừng
Dựa vào tính chất 3, ta có thể thực hiện giai đoạn 1 bằng cách bắt đầu từ heap
mặc nhiên an/2+1, an/2+2,…,an, lần lượt thêm vào các phần tử an/2, an/2-1,

…,a1. ta sẽ nhận được Heap theo mong muốn. Như vậy giải đoạn 1 tương đương
với n/2 lần thực hiện bước 2 của giai đoạn 2.
3. Giải bài toán trên maple
> parent:=i->floor(i/2);
>
>
5
>
>
6
>
>
>
>
>
>
>
>
7
>
>
>
>
>
>
>
>
>
II. Thuật toán quick sort
1 Mô tả bài toán

8
Sắp xếp nhanh (Quicksort), còn được gọi là sắp xếp kiểu phân chia (part sort) là
một thuật toán sắp xếp phát triển bởi C.A.R. Hoare, dựa trên phép phân chia
danh sách được sắp thành hai danh sách con. Phương pháp này là minh họa rõ
ràng nhất Để sắp xếp một danh sách a[1…n] ta chia nó thành hai danh sách bằng
cách so sánh từng phần tử của danh sách với một phần tử được chọn làm phần tử
chốt.
Những phần tử nhỏ hơn phần tử chốt được đưa về phía trước và nằm trong danh
sách con thứ nhất, các phần tử lớn hơn chốt được đưa về phía sau và thuộc danh
sách đứng sau. Cứ tiếp tục chia như vậy tới khi các danh sách con đều có độ dài
bằng 1.
Danh sách a[1…n]:
Danh sách 1 gồm: a[1…k] < X
Danh sách 2 gồm: a[(k+1) …n] > X
a < X
a = X
a > X
Ở đây ta thấy xuất hiện 3 danh sách con, trong đó:
Danh sách thứ 2 đã được sắp xếp. Nếu danh sách 1 và 3 chỉ có một phần tử thì
dãy a[i…n] đã được sắp xếp xong. Nếu danh sách 1 và 3 có hơn một phần tử thì
dãy ban đầu chỉ có thứ tự khi các dãy con 1, 3 được sắp. Để sắp xếp dãy con 1 và
3, ta lần lượt tiến hành việc phân hoạch từng dãy con theo cùng phương pháp
phân hoạch dãy ban đầu vừa trình bày.
4. Thuật giải
Giải thuật phân hoạch dãy a[1…n] thành hai dãy con gồm 3 bước:
9
Bước 1: chọn tùy ý 1 phần tử a[k] trong dãy làm giá trị mốc.
L ≤ k ≤ R : a[k] =X;
i = L; j = R;
Gợi ý các cách chọn phần tử mốc

Chọn phần tử đứng đầu hoặc đứng cuối làm phần tử chốt.
Chọn phần tử đứng giữa danh sách làm phần tử chốt.
Chọn phần tử trung vị trong 3 phần tử đứng đầu, đứng giữa và đứng cuối làm
phần tử chốt.
Chọn phần tử ngẫu nhiên làm phần tử chốt. (Cách này có thể dẫn đến khả năng
rơi vào các trường hợp đặc biệt)
Bước 2: Phát hiện và hiệu chỉnh cặp phần tử a, a[j] nằm sai chỗ:
Bước 2a: Trong khi (a < X) i++;
Bước 2b: Trong khi (a[j] > X) j++;
Bước 2c: Nếu i < j // a ≥ X ≥ a[j] mà a[j] đứng sau a
Hoán vị ( a, a[j]);
Bước 3: Nếu i < j; Lặp lại Bước 2
// chưa xét hết mảng
Nếu I > j; Dừngcho chiến lược chia để trị.
5. Giải bài toán trên Maple
10
>
11
>
>
>
>
12
>
>
>
>
>
>
>

>
13
>
>
>
>
>
14

×