搭配green judge解題系統
Special thanks to 台中女中sagit老師 <(_ _)>
上一章:副函式與遞迴
下一章:貪婪演算法
回目錄:國立科學園區實驗中學C++程式語言自學講義
將陣列裡的元素重新安排位置
讓它們從小到大、或是從大到小排好
就是排序
例如原本的陣列為 0、3、16、2、9
從小到大排序後為 0、2、3、9、16
從大到小排序後為 16、9、3、2、0
要達成這樣的效果
有許多的排序演算法可以實現
以下動畫GIF皆取自Wikimedia
就像氣泡會從水底浮到水面一樣
每次比對相鄰的兩個,讓大的那個移到後面去
第一輪做完後 會發現最大的數字被移到了最後面
第二輪做完後 會發現第二大的數字被移到了倒數第二個
過了n輪以後就會按照從小到大排好
for(int i=0;i<n;i++){
for(int j=0;j<n-1-i;j++){
if(arr[j]>arr[j+1])
swap(arr[j], arr[j+1]);
}
}
像整理手中的撲克牌一樣
每次都揪出最小的放到最前面,再也不去動它
一共要揪n次
就會按照從小到大排好
動畫中黃色的數字是已經排好、不再去動的
每一輪都會在剩下的白色中找最小的
用藍色掃過每一個數字
紅色紀錄目前看到的最小值
總共要進行n輪
for(int i=0;i<n;i++){
int idx=i; //先假設第i個位置是最小的,之後找到更小再代換
for(int j=i;j<n;j++){
if(arr[j]<arr[idx]){
idx=j;
}
}
swap(arr[i], arr[idx]);
}
這也和整理撲克牌的方法滿像的
每一輪都從尚未整理的牌中拿出一張
然後看它應該要被安插到已經整理好的牌堆的哪個位置
總共要進行n輪
for(int i=0;i<n;i++){
for(int j=i;j>=1;j--){
if(arr[j]<arr[j-1])
swap(arr[j], arr[j-1]);
}
}
要將數字按照順序排好
請想好兩件事
以下程式將示範
int arr[10]={0,3,1,6,0,2,9,84,12,31}; //一個沒排序過的亂亂陣列
for(int i=0;i<10;i++){
for(int j=0;j<9;j++){
if(arr[j]>arr[j+1])
swap(arr[j], arr[j+1]);
}
}
//印出來看是不是真的從小到大排好了
for(int i=0;i<10;i++){
cout<<arr[i]<<" ";
}
【學生練習題】
其實字串也可以直接比大小喔
會先比第一個字,如果一樣再比第二個字…以此類推
以下程式將示範
string arr[5]={"Hello", "Hi", "QQ", "GG", "Bang"};
for(int i=0;i<5;i++){
for(int j=i;j>=1;j--){
if(arr[j]<arr[j-1])
swap(arr[j], arr[j-1]);
}
}
for(int i=0;i<5;i++){
cout<<arr[i]<<endl;
}
【學生練習題】
如果兩個東西要比大小,
是要先比其中一個特徵,一樣的話再比下一個,再一樣就再比下一個…的話
就不是只用大於小於就可以解決囉
要自己寫一段if else~
【例題】
輸入一個n
接著輸入n個人的名字以及出生年月日
依照年分->月份->日期的順序排序
也就是,先比年分,再比月份,再比日期
輸出排序過後的每個人的名字
既然有姓名和年月日
那我們就開四個陣列來分別存姓名和年月日吧
string name[50];
int year[50];
int month[50];
int date[50];
int n;
cin >> n;
for(int i=0;i<n;i++{
cin >> name[i];
cin >> year[i];
cin >> month[i];
cin >> date[i];
}
接下來要排序囉
以下程式將示範
1.年份小的在前面,若一樣則月份小的在前面,若又一樣則日期小的在前面
2.來用個插入排序法吧
for(int i=0;i<n;i++){
for(int j=i;j>=1;j--){
if(year[j]<year[j-1]){
swap(name[j], name[j-1]);
swap(year[j], year[j-1]);
swap(month[j], month[j-1]);
swap(date[j], date[j-1]);
}
else if(year[j]==year[j-1]&&month[j]<month[j-1]){
swap(name[j], name[j-1]);
swap(year[j], year[j-1]);
swap(month[j], month[j-1]);
swap(date[j], date[j-1]);
}
else if(year[j]==year[j-1]&&month[j]==month[j-1]&&date[j]<date[j-1]){
swap(name[j], name[j-1]);
swap(year[j], year[j-1]);
swap(month[j], month[j-1]);
swap(date[j], date[j-1]);
}
}
}
最後再依序輸出他們的名字
for(int i=0;i<n;i++){
cout << name[i] << endl;
}
【學生練習題】
上一章:副函式與遞迴
下一章:貪婪演算法
回目錄:國立科學園區實驗中學C++程式語言自學講義