求解最大值与最小值-分治算法

一、概述


无论是最好、最坏或者平均情况,该MaxMin分治算法所用的比较次数都是3n/2-2。
而实际中,任何一种以元素比较为基础的找最大值最小值元素的算法,其元素比较次数的下界为3n/2-2。
因此,从此种情况上分析,该算法是最优的。
但由于需要log(n)+1级的递归,而每次递归调用需要将 i j fmax fmin 和返回地址的值进行压栈,故需要额外占用一些内存空间。
当然,压出栈过程中也会带来时间开销。
特别是A中元素的比较次数和整数i j 的比较次数相近时,递归求最大最小算法未必比直接求解算法效率高。


二、伪代码


     //递归求最大最小值的分治算法
MaxMin(i,j,fmax,fmin) //A[1:n]是n元数组,
     //参数i,j :1≤i≤j≤n,使用该过程将数组
     // A[i..j]中的最大最小元分别赋给fmax和fmin。
      global n, A[1..n]; 
      integer i, j;
  if i=j then   
       fmax:=A[i]; fmin:=A[i]; 
    //子数组A[i..j]中只有一个元素
  else if i=j-1 then 
    //子数组A[i..j]中只有两个元素
      if A[i]then
        fmin:=A[i]; fmax:=A[j];
      else fmin:=A[j]; fmax:=A[i];
      end{if}
  else   //子数组A[i..j]中的元素多于两个
        mid:=(i+j)/2; 
        MaxMin(i, mid, lmax, lmin);
        MaxMin(mid+1, j, rmax, rmin);
        fmax:=max(lmax, rmax);
        fmin:= minlmin, rmin);     
  end{if}
end{MaxMin} 

三、时间复杂度


求解最大值与最小值-分治算法_第1张图片


四、源码示例


// max_min.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#define n 10
int A[n];
int Max(int a, int b)
{
    return ((a >= b) ? a : b);
}
int Min(int a, int b)
{
    return ((a <= b) ? a : b);
}
void MaxMin(int i, int j, int &fmax, int &fmin)
{
    int mid;
    if (i == j)
    {
        fmax = A[i];
        fmin = A[i];
    }
    else if(i==j-1)
    {
        if (A[i] < A[j])
        {
            fmin = A[i];
            fmax = A[j];
        }
        else
        {
            fmin = A[j];
            fmax = A[i];
        }
    }
    else
    {
        int lmax, lmin, rmax, rmin;
        mid = floor((i + j) / 2);
        MaxMin(i, mid, lmax, lmin);
        MaxMin(mid + 1, j, rmax, rmin);
        fmax = Max(lmax, rmax);
        fmin = Min(lmin, rmin);
    }
}
int main()
{
    for (int i = 0; i < n; i++)
    {
        scanf_s("%d", &A[i]);
    }   
    int fmax, fmin;
    MaxMin(0, n-1, fmax, fmin);
    printf("\n\n最大值为:%d\n最小值为:%d\n\n", fmax, fmin);

    return 0;
}


你可能感兴趣的:(C语言,算法思想)