分治
简单而言就是分而治之!
一、fen( ):先把一组数组不断对半分开,直到每一份都只有一个数为止。
如下图:
5 2 6 1 4 3 7
↓ sort ↓
5 2 6 1 4 3 7
↓ sort ↓ ↓ sort ↓
5 2 6 1 4 3 7
↓ sort ↓ ↓ sort ↓ ↓ sort ↓
5 2 6 1 4 3
♥
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
二、he( ):把它们处理好后再合并。
如下图(从小到大排序):
5 2 6 1 4 3 7
↓ merge ↓ ↓ merge ↓ ↓merge↓ ↓
2 5 1 6 3 4 7
↓ merge ↓ ↓ merge ↓
1 2 5 6 3 4 7
↓ merge ↓
1 2 3 4 5 6 7
一道经典例题 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
有 n 个数,把它们从小到大排序后输出。
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
代码:
#include <bits/stdc++.h> //未完善
using namespace std;
int n,a[100000],tmp[1000000];
void he(int tmp[],int l,int r){
int mid=(l+r)/2;
int leftStart=l,leftEnd=mid;
int rightStart=mid+1,rightEnd=r;
int cpos=l;
while(leftStart<=leftEnd && rightStart<=rightEnd){
if(a[leftStart]<=rightStart){
tmp[cpos++]=a[leftStart++];
//cout<<tmp[cpos]<<" ";
}
else{
tmp[cpos++]=a[rightStart++];
//cout<<cpos<<" ";
}
}
while(leftStart<=leftEnd){
tmp[cpos++]=a[leftStart++];
//cout<<tmp[cpos]<<" ";
}
while(rightStart<=rightEnd){
tmp[cpos++]=a[rightStart++];
//cout<<tmp[cpos]<<" ";
}
for (int i=l;i<=r;i++){
a[i]=tmp[i];
}
}
void fen(int tmp[],int l,int r){
if(l!=r){
int mid=(l+r)/2;
for (int i=l;i<=r;i++){
cout<<a[i]<<" ";
}
cout<<endl;
fen(tmp,l,mid);
fen(tmp,mid+1,r);
he(tmp,l,r);
}
}
int main (){
cin>>n;
for (int i=1;i<=n;i++)cin>>a[i];
fen(tmp,1,n);
for (int i=1;i<=n;i++)cout<<a[i]<<" ";
}