分治策略

1.分治策略的思想

分治就是把规模大的问题,划分为彼此独立的,规模小的结构相似子问题。直到划分到子问题能直接求解时,就通过递归来实现求解所有子问题,并合并所有解。因此递归和分治可以说是孪生兄弟。

2.分治步骤

第(1)步:分 把一个规模大的问题,划分成若干结构相同,能独立求解的子问题。

第(2)步:治通过递归,求出每个子问题的解。

第(3)步:合并把所有子问题的解,合并成一个更大规模问题的解。

这里举个例子:假设我们要数一堆珠子,假设珠子特别多一个数不完了。这时候数珠子就是一个规模很大的问题。第一步:于是我们把珠子分成很多份,让很多去去数一份。这时候就发现数珠子是一个独立结构相似的问题。第二步:每个人都数出自己那一份珠子个数。第三步:把每个人数出个数相加就是总共珠子数。这里相当于合并了解。

3.二分查找

#include<iostream>
using  namespace std;

int searchvalue(int left,int right,int *arr,int x)
{     
    if(right < 1 || arr == NULL)return -1; //判断一下外界传的参数是否正确     
    int pos = -1;      
    if(left <= right)     
    {          
            int  mid = (right-left+1)/2+left;         
            if(x < arr[mid]) return pos = searchvalue(left,mid-1,arr,x);          
            else if(x >arr[mid]) return pos = searchvalue(mid+1,right,arr,x);          
            else          
            {               
                while(mid > left && arr[mid-1] == x) //这里防止同一个出现多个x,让pos保存最左边的x下标 
                {                             
                    --mid;               
                }               
                    pos = mid;         
            }     
    }          
    return pos;
}

int main()    
{     
    int arr[] = {12,13,15,17,43,54,67,76,86,90,92};     
    int n = sizeof(arr)/sizeof(arr[0]);     
    int x = 15;      
    int pos = searchvalue(0,n-1,arr,x);     
    printf("%d\n",pos);     
    return 0;
}

斐波那契数列

#include<iostream>
using namespace std;

//非递归
int fun(int n)
{
     int a = 1, b = 1, c = 1;
     int i = 2;
     for(i=2; i<n; i++)
     {
          c = a+b;
          a = b;
          b =c;
     }
     return c;
}


//朴素递归
int fun1(int n)
{
     if(n <= 2)
     {
          return 1;
     }
     return fun(n-2)+fun(n-1);
}

//改良后的递归,时间复杂度比朴素小很多
int fun2(int n,int a,int b)
{
     if(n < 3) return a;
     else return fun2(n-1,a+b,a);
}

int fac(int n)
{
     int a = 1;
     int b = 1;
     return fun2(n,a,b);
}

点赞