第二章作业
对分治法的感悟:
- 基本思想:分治法其实就是将一个规模为N的问题分解为k个规模较小的子问题,这些子问题互相独立且与原问题相同。递归地解这些子问题,然后将各子问题的解合并并得到原问题的解。一般在分治法中和基础的程序是递归算法。
- 例子:
1)二分搜索技术(P书17):
二分搜索算法的基本思想是将n个元素分成个数大致相同的两半,取a[n/2]与x作比较。如果x=a[n/2],则找到x,算法终止;如果x<a[n/2],则只在数组a左半部继续搜索x;如果x>a[n/2],则只在数组右半部继续搜索x。算法可描述为:
int search(int a[], int x, int n) { int left = 0; int right = n - 1; while(left <= right) { int middle = (left + right) / 2; if(x == a[middle]) return middle; if(x > a[middle]) left = middle + 1; else right = middle - 1; } return -1; }
最坏情况下的时间复杂度为O(logn)。
2)合并排序(P书22):
将待排元素分成大小大致相同的两个子集合,分别对两个子集合进行排序,最终将排好的子集合合并成所要求的排好序的集合。算法可描述为:
void MergeSort(int a[], int left, int right) { if(left < right) { int i = (left + right) / 2; //取中点 MergeSort(a, left, i); MergeSort(a, i + 1, right); Merge(a, b, left, i, right); //合并到数组b Copy(a, b, left, right); //复制回数组a } }
合并排序计算时间T(n)得T(n)=O(nlogn)。
3.总结:
分治法往往可以把一些复杂问题简单化,只要是要找到相同类型的子问题和临界点,这样就可以快速解决问题。与此同时,分治法求T(n)也是一大难点,需要记熟公式和比较对象。
结对编程感受
我和我的搭档在做第一题时浪费了很多时间,是由于在极端情况下总是达不到要求。我在我的搭档那里学到了如何运用简单的步骤来检验自己代码中出的错误,只要不断地带入数值,输出其中的一个过程相关的值,就可以较为快捷地找到自己的错误在哪里。
合作地很愉快,可以更加便捷地交流自己的解题想法,互利互惠。