归并排序
原创、转载请注明出处
分治:
划分问题
递归求解
合并问题
#include<iostream> using namespace std; void f(int A[], int x, int y, int T[])//[x,y) { if(y - x == 1)//区间内只有1个元素时不用改变顺序,作为边界 { return ; } int mid = x + (y - x) / 2;//使中点趋向左端而不是零点 f(A, x, mid, T);//[x,mid) f(A, mid, y, T);//[mid,y) int pos1 = x, pos2 = mid, pos3 = 0; while(pos1 < mid || pos2 < y)//2个序列都为空 { if(pos2 >= y || (A[pos1] <= A[pos2] && pos1 < mid))//第二个序列是空或者2个序列都非空且1序列头小于2序列头 { T[pos3++] = A[pos1++]; } else//第一个序列是空或者2个序列都非空2序列头小于2序列头 { T[pos3++] = A[pos2++]; } } for(int i = x; i < y; i ++)//临时数组复制回A数组 { A[i] = T[i - x]; } } int main() { int n,A[1000],T[1000]; cin >> n; for(int i = 0; i < n; i ++) { cin >> A[i]; } f(A, 0, n, T); for(int i = 0; i < n; i ++) { cout << A[i] << ' '; } cout << endl; return 0; }
20
6 1 5 4 8 3 9 12 51 11 15 14 13 25 69 47 56 74 26 78
note:
1、T临时数组
2、合并2个序列时,注意一个为空的情况
3、好的分类可简化代码的书写,比如这里的pos2 >= y || (A[pos1] <= A[pos2] && pos1 < mid),同时注意这里或者符号前后的内容不能逆。