將原問題劃分成若干個規模較小而結構與原問題相同或相似的子問題,然後分別解決這些子問題,最後合併子問題的解,得到原問題的解的方法,廣義上講稱爲分治。嚴格意義上,子問題數爲1的情況稱爲減治,大於1的情況稱爲分治。而分治既可以通過遞歸實現,也可通過非遞歸實現,遞歸只是實現分治的一種手段。
遞歸的兩個關鍵是遞歸邊界和遞歸式。
階乘運算和Fibonacci數列分別是減治和分治的典型例子
下面給出一個求全排列的遞歸函數
bool hashtable[maxn]={false};
int p[maxn]
void cal(int pos)
{
if(pos==n+1)
{
for(int i=1;i<=n;i++)
{
printf("%d",p[i]);
}
printf("\n");
return ;
}
for(int i=1;i<=n;i++)
{
if(hashtable[i]==false)
{
p[pos]=i;
hashtable[i]=true;
cal(pos+1);
hashtable[i]=false;
}
}
}
利用全排列,我們可以解決n皇后問題,區別只是在遞歸邊界考慮任意兩個皇后是否在對角線上,或者在每次填充皇后時,考慮該皇后是否和之前的皇后在一條對角線上,即回溯。