记录在PTA上做的几道关于分治与递归的题目笔记
Time:2021.3.11
一、归并排序 (递归法)
函数接口:
void Merge(SqList L,int low,int m,int high);//合并两个有序序列
void MergeSort(SqList L,int low,int high); //递归切分序列
函数代码
void Merge(SqList L,int low,int m,int high)
{
int temp[high];
int i=low,j=m+1;
int k=0;
while (i <= m && j <= high) {
if(L.elem[i] <= L.elem[j])
temp[k++] = L.elem[i++];
else
temp[k++] = L.elem[j++];
}
while (i <= m)
temp[k++] = L.elem[i++];
while (j <= high)
temp[k++] = L.elem[j++];
for (i=0; i<k; i++)
L.elem[low+i] = temp[i];
}
void MergeSort(SqList L,int low,int high)
{
/*用分治法进行二路归并排序*/
int mid;
if(low<high) /*区间长度大于1*/
{
mid=(low+high)/2; /*分解*/
MergeSort(L,low,mid); /*递归地对low到mid序列排序 */
MergeSort(L,mid+1,high); /*递归地对mid+1到high序列排序 */
Merge(L,low,mid,high); /*归并*/
}
}
二、二分搜索(分治法)
函数接口
int binsearch(int A[],int key,int low,int high);
代码如下
int binsearch(int A[],int key,int low,int high)
{
int mid;
mid=(low+high)/2;
if(A[mid]==key)
return mid;
if(A[mid]>key)
binsearch(A,key,low,mid-1);
else
binsearch(A,key,mid+1,high);
}
三、快速排序(分治法)
函数接口
int Partition(SqList &L,int low,int high);//实现一趟划分。
void QSort(SqList &L,int low,int high);
完整代码
int Partition(SqList &L,int low,int high)//实现一趟划分。
{
int priv=L.r[low].key;
int i,j;
i=low; j=high;
while(i<j) {
while (L.r[j].key>=priv && i<j)
j--;
L.r[i].key=L.r[j].key;
while (L.r[i].key<=priv && i<j)
i++;
L.r[j].key=L.r[i].key;
}
L.r[i].key=priv;
return i;
}
void QSort(SqList &L,int low,int high)
{
int priv;
if(low<high) {
priv=Partition(L,low,high);
QSort(L,low,priv-1);
QSort(L,priv+1,high);
}
}
四、最大最小问题(分治法)
函数接口
void maxmin(int A[],int &e_max,int &e_min,int low,int high);
函数接口
void maxmin(int A[],int &e_max,int &e_min,int low,int high)
{
int a,b,c,d;
if(high-low<=1) {
e_max=max(A[high],A[low]);
e_min=min(A[high],A[low]);
}
else {
int mid=(low+high)/2;
maxmin(A,a,c,low,mid);
maxmin(A,b,d,mid+1,high);
e_max=max(a,b);
e_min=min(c,d);
}
}
五、最大次大问题(分治法)
函数接口
void max1max2(int a[],int low,int high,int &max1,int &max2);
void max1max2(int a[],int low,int high,int &max1,int &max2)
{
int k,b,c,d;
if(low==high) {
max1=a[low];
max2=INF;
}
else if(low==high-1) {
max1=max(a[high],a[low]);
max2=min(a[high],a[low]);
}
else {
int mid=(low+high)/2;
max1max2(a,low,mid,k,c);
max1max2(a,mid+1,high,b,d);
if(k>b) {
max1=k;
max2=max(c,b);
}
else {
max1=b;
max2=max(k,d);
}
}
}
总结
在归并排序中函数接口为:void Merge(SqList L,int low,int m,int high);//合并两个有序序列
这里函数返回值为空,形参也没有用到指针或传引用,但是函数的形参却可以改变实参