30
1 主主 : Sorting ( 主主 ) 主主主主 主主主 sorting 主主主 sorting 主主 主主主主 qsort 主主主主 : A.299 主主主主

主題 : Sorting ( 排序 )

Embed Size (px)

DESCRIPTION

主題 : Sorting ( 排序 ). 解題技巧 什麼是 sorting ? 基本的 sorting 方法 如何使用 qsort 例題講解 : A.299 歷年題目. 什麼是 sorting ?. 將給定的資料按照 特定的順序 排列好 由小到大 由大到小 例: 1, 7, 9, 5, 3 由小到大: 1, 3, 5, 7, 9 由大到小: 9, 7, 5, 3, 1. 什麼是 sorting ?. 只有數字能比大小嗎? John  Bob 小明  小華 只要能 定義大小關係 ,就可以 sort - PowerPoint PPT Presentation

Citation preview

Page 1: 主題 : Sorting ( 排序 )

1

主題 : Sorting ( 排序 ) 解題技巧

什麼是 sorting ? 基本的 sorting 方法 如何使用 qsort

例題講解 : A.299 歷年題目

Page 2: 主題 : Sorting ( 排序 )

2

什麼是 sorting ? 將給定的資料按照特定的順序排列好

由小到大 由大到小

例: 1, 7, 9, 5, 3 由小到大: 1, 3, 5, 7, 9 由大到小: 9, 7, 5, 3, 1

Page 3: 主題 : Sorting ( 排序 )

3

什麼是 sorting ? 只有數字能比大小嗎?

John Bob 小明 小華

只要能定義大小關係,就可以 sort J 在 B 之後 John > Bob “明”筆畫比“華”少 小明 < 小華

Page 4: 主題 : Sorting ( 排序 )

4

常見的 sorting 演算法 bubble sort merge sort quick sort heap sort integer sort

Page 5: 主題 : Sorting ( 排序 )

5

Bubble sort 原理

就像氣泡會往上浮一樣,小的數字必須要往前進,而大的數字就必須往後退 每次比較相鄰的兩個數字,然後將小的放在前面的位置,而大的放在後面的位置

Page 6: 主題 : Sorting ( 排序 )

6

Example

1 7 9 5 3

1 7 9 5 3

1 7 5 9 3

1 7 5 3 9

1 7 5 3 9

1 5 7 3 9

1 5 3 7 9

1 5 3 7 9

1 3 5 7 9

1 3 5 7 9

stage 1

stage 2

stage 3

stage 4

Page 7: 主題 : Sorting ( 排序 )

7

swap 方法 1:

寫一個 swap 的 function ,每次需要的時侯就可以 call 來用 注意不能直接傳值進去

Page 8: 主題 : Sorting ( 排序 )

8

swap example: 將兩個整數互換

void swap( int *a, int *b){

int tmp;

tmp = *a; *a = *b; *b = tmp;

}

int x, y;

swap( &x, &y);

Page 9: 主題 : Sorting ( 排序 )

9

swap 方法 2:

利用 #define 定義 swap 變數要記得宣告

Page 10: 主題 : Sorting ( 排序 )

10

swap example: 將兩個整數互換

#define swap( x, y) (( t) = ( x), ( x) = ( y), ( y) = ( t))

int t;

swap( x, y);

Page 11: 主題 : Sorting ( 排序 )

11

for ( i = 0 ; i <= n – 1 ; i++ ) for ( j = 0 ; j <= n – 2 ; j++)

if ( num[ j ] > num[ j + 1] )swap(&num[ j ] , &num[ j +

1]);

C code

代 n – i – 2 會更快

Page 12: 主題 : Sorting ( 排序 )

12

Stable sort 若是要 sort 的東西之中有大小相同的,如果 sort 完之後大小相同的排法是依照兩個東西 input 的順序排列的話,稱為

stable sort ,如果不保證一定按照 input 的順序排的話,稱為 non-stable sort input: 3 5 2 1 3 4 stable sort: 1 2 3 3 4 5

Page 13: 主題 : Sorting ( 排序 )

13

Parallel array 有時後在寫程式時為了方便起見會開幾個陣列來儲存而不是用 structure ,這時如果按其中一個

array 的值來 sort 的話,要記得所有的 array 都要跟著做一樣的動作 例 :

a[i] 代表身高, b[i] 代表體重,現在想按照身高來做 sort ,則 b[i] 也應該做相對應的變動才能夠讓 a[i] 和 b[i] 代表同一個人的身高體重

在 swap(a[i], a[j]) 時也應該做 swap(b[i], b[j]) 的動作

Page 14: 主題 : Sorting ( 排序 )

14

qsort C 內建的 sort function ,一般來說比用

bubble sort 來的快。 需要自己寫一個 compare function

Page 15: 主題 : Sorting ( 排序 )

15

Example: qsortint tbl[] = {5, 6, 12, 3, 20, 8};

int comp_func( const void *a, const void *b){ int c, d; c = *(int *)(a); d = *(int *)(b); if (c > d) return (1); else if (c == d) return (0); else return (-1);}

qsort(tbl, sizeof(tbl) / sizeof(tbl[0]), sizeof(tbl[0]), comp_func);

陣列指標 要 sort 的個數 每個要 sort 的 element 的大小compare function

Page 16: 主題 : Sorting ( 排序 )

16

Example: qsort

char tbl[][10] = {“Hello”, “OK”, “Test”, “BBS”, “Book”, “C”};

int comp_func( const void *a, const void *b){ char *c, *d; c = (char *)(a); d = (char *)(b); return (strcmp(c, d));}

qsort(tbl, sizeof(tbl) / sizeof(tbl[0]), sizeof(tbl[0]), comp_func);

Page 17: 主題 : Sorting ( 排序 )

17

Example: qsort#include <stdio.h>int num[5] = {1, 7, 9, 5, 3 };int comp_func(const void *a, const void *b){int c, d;

c = *(int *)(a); d = *(int *)(b); return ( c – d );}int main(void){

qsort(num, sizeof(num)/sizeof(num[0]), sizeof(num[0]), comp_func);

/* qsort(num, 5, sizeof(num[0]), comp_func); */

return 0;}

Page 18: 主題 : Sorting ( 排序 )

18

qsort and bubble sort bubble sort

執行速度較慢 程式好寫好記,不容易忘

qsort 執行速度較快 需要自己寫 compare function 不熟的話容易忘記格式

Page 19: 主題 : Sorting ( 排序 )

19

例題講解 : A.299(http://acm.uva.es/p/v2/299.html)

有一列火車總共有 L 節車廂,每節車廂都有個編號 ( 從 1 ~ L) 。現在車廂的順序亂掉了,而站長希望能把車廂的順序由 1 到 L 排好。唯一能做的方法是把相鄰的兩個車廂順序對調,請問,最少需要做幾次的車廂順序對調工作,而能讓車廂的順序由 1 到 L 排好。 L 最大到 50

Page 20: 主題 : Sorting ( 排序 )

20

Sample input/outputSample input:331 3 244 3 2 122 1

Sample output:Optimal train swapping takes 1 swaps.Optimal train swapping takes 6 swaps.Optimal train swapping takes 1 swaps.

總共會有幾組 test case

車廂的長度

車廂的編號

Page 21: 主題 : Sorting ( 排序 )

21

讀進 input 需要的資料結構 int case_num

總共有幾個 test case

int L 車廂的長度

int num[50] 每個車廂的編號 因為 L 最大只有 50 ,所以開一個長度 50 的整數陣列就夠了

Page 22: 主題 : Sorting ( 排序 )

22

分析 1 3 2

noswap ( 1, 3) 1 3 2 swap ( 2, 3) 1 2 3 noswap ( 1, 2) 1 2 3

4 3 2 1 swap ( 4, 3) 3 4 2 1 swap ( 4, 2) 3 2 4 1 swap ( 4, 1) 3 2 1 4 swap ( 3, 2) 2 3 1 4 swap ( 3, 1) 2 1 3 4 swap ( 2, 1) 1 2 3 4

Page 23: 主題 : Sorting ( 排序 )

23

解法 換火車車廂的順序跟 bubble sort 的順序是一樣的 照著 bubble sort 的方法去做,每當 sw

ap 發生的時候就在總次數的地方加一,最後得到的數字就是最少需要換的次數

Page 24: 主題 : Sorting ( 排序 )

24

Program structureread_case_num();for ( i = 0; i < case_num; i++){

read_train_length();read_train_number();bubble_sort();// 每次 swap 時把 counter 往上加output_optimal_solution();

}

Page 25: 主題 : Sorting ( 排序 )

25

Program#include <stdio.h>#define swap( x, y) (( t) = ( x) , ( x) = ( y), ( y) = ( t))int main(void){

int i, j, k, t, L, case_num, counter, num[50];freopen(“data.in”, “r”, stdin); // 若是要送到 acm online judge ,則這行要拿掉scanf(“%d”, &case_num);for ( i = 0; i < case_num; i++){counter = 0;scanf(“%d”, &L);for( j = 0; j < L; j++)scanf(“%d”, &num[j]);for( j = 0; j < L – 1; j++)for( k = 0; k < L – j – 1; k++)if ( num[k] > num[k + 1]) {counter++;swap( num[k], num[k + 1]);}printf(“Optimal train swapping takes %d swaps. \n”, counter);}return 0;

}

Page 26: 主題 : Sorting ( 排序 )

26

例題講解 : H.88.4http://www.cc.nccu.edu.tw/info_race88/Q.pdf

了解題意 input 格式、範圍, output 格式、要求 分析解法,需要什麼資料結構 架構程式,上機實作

Page 27: 主題 : Sorting ( 排序 )

27

漏洞與陷阱 漏洞

題目寫著“金、銀、銅牌的分配約為 1: 2: 3” ,那要是人數不是 6 的倍數怎麼辦? 要是有同分的人落在金、銀牌之間的分界處,該怎麼解決? Output 格式,欄位有多寬?不然該怎麼對齊? 輸出 3 中,如果有得獎牌數一樣的國家,該 output 一個或是全部 output ?有順序分別嗎?

陷阱 人名有可能中間有空白字元分開,讀 input 時要特別小心

Page 28: 主題 : Sorting ( 排序 )

28

解法 依照得分高低排序

只要能正確的讀入 input ,排序,再 output 就好 計算各種獎牌數量

加個 counter 計算一下獎牌數量 找出得獎牌最多的國家

用陣列計算每個國家得獎的數量 計算平均數、最高分、最低分和全距

簡單的數學式

Page 29: 主題 : Sorting ( 排序 )

29

解題重點 如何正確的讀入 input

C 有許多內建的 string function 可以利用,請期待明天的教學

Page 30: 主題 : Sorting ( 排序 )

30

歷年題目 練習題

A.10008 What’s Cryptanalysis http://acm.uva.es/p/v100/10008.html

A.10057 A Mid-summer Night’s Dream http://acm.uva.es/p/v100/10057.html

A.612 DNA Sorting http://acm.uva.es/p/v6/612.html

挑戰題 A.10125 Sumsets

http://acm.uva.es/p/v101/10125.html

其他歷年題目 H.88.4

http://www.cc.nccu.edu.tw/info_race88/Q.pdf H.89.1 對對碰

http://www.cc.nccu.edu.tw/info_race89/doc/final_program.doc