目录
1.定义
2.例子
3.注意
1.定义
分治法(Divide and Conquer)是一种解决问题的算法设计策略,它将一个大问题分解成若干个规模较小且结构与原问题相似的子问题,然后递归地解决这些子问题,最后将子问题的解合并起来得到原问题的解。
分治法的一般步骤包括:
-
分解(Divide):将原问题分解成若干个规模较小的子问题,这些子问题与原问题的结构相同,并且可以相互独立地解决。
-
征服(Conquer):递归地解决这些子问题。如果子问题的规模足够小,可以直接求解而不再进行分解。
-
合并(Combine):将子问题的解合并起来,得到原问题的解。
分治法通常适用于以下类型的问题:
- 可以被分解为若干个相互独立且结构相似的子问题。
- 子问题的解可以合并为原问题的解。
- 递归求解子问题的效率高。
分治法在算法设计中有着广泛的应用,例如快速排序、归并排序、大整数乘法等问题都可以通过分治法来解决。这种算法设计策略能够有效地降低问题的复杂度,提高算法的效率。
2.例子
以归并排序为例。假设实现归并排序的函数名为 sort
。明确该函数的作用,对传入的一个数组排序。这个问题显然可以分解:给一个数组分成左右两个部分,然后对该数组排序即为给该数组的左右两半分别排序,最后再合并成一个数组。
void sort(一个数组) {if (可以很容易处理的条件) return;sort(左半个数组);sort(右半个数组);merge(左半个数组, 右半个数组);
}
传给它半个数组,那么处理完后这半个数组就已经被排好了。分治算法的套路是分解 -> 解决(触底)-> 合并(回溯),先左右分解,再处理合并,回溯就是在退栈,即相当于二叉树的后序遍历。merge
函数的实现方式与两个有序链表的合并一致。
3.注意
如果各子问题是不独立的,则分治法要重复地解公共的子问题,也就做了许多不必要的工作。此时虽然也可用分治法,但一般用 动态规划 较好。