递归函数实现
应用于二分查找 归并排序等
public void getMaxByBinary(int[] arr){
1 return process(arr,0,arr.length-1);
}
public int process(int[] arr,int L,int R){//f(0,3)
2 if(L==R){
3 return arr[L];
}
4 int mid = L+((R-L)>>1);
5 int leftMax = process(arr,L,mid);
6 int rightMax = process(arr,mid+1,R);
7 return Math.max(leftMax,rightMax);
}
手动添加的行号 现给定数组为{1,3,4,2}
执行框架
f(0,3)
3↗ ↖4
f(0,1) f(2,3)
1↗ ↖3 4↗ ↖2
f(0,0) f(1,1) f(2,2) f(3,3)
系统内部使用栈实现这一流程
在执行到行号1的位置 调用process函数
f(0,3) 执行过程中记录 L=0 R=3 mid=1 leftMax=? 以及执行到的行号5 压入栈
在执行到行号为5的时候 又开始调用process函数
f(0,1) 执行过程中记录 L=0,R=1 mid =0 leftMax=? 以及执行到的行号5 压入栈
在执行到行号为5的时候 又开始调用process函数
f(0,0) 此时满足if(LR) 执行return arr[L]; 函数弹出栈 并将arr[L]赋值与f(0,1)中保存的leftMax=1,此时f(0,1)函数继续行号5往下执行行号6的代码保存rightMax=?
process(arr,mid+1,R) 中的参数就是f(0,1)中的参数 process(arr,0+1,R)在这里看成f(1,1) 此时满足if(LR) 执行return arr[L]; f(1,1)函数弹出 并将 arr[L]=3 赋值给此时f(0,1)函数中的rightMax=3,
此时又会执行行号6以下的代码return Math.max(leftMax,rightMax); 求出值为左侧最大值为3。
此时的栈顶为f(0,3) L=0 R=3 mid=1 leftMax=3 由于在上次执行到行号为5的位置,现在开始执行行号为6的位置 int rightMax = process(arr,mid+1,R); f(2,3)
重复上述f(0,1)的执行过程返回rightMax = 4 在执行 Math.max(leftMax,rightMax);
结果为4
时间复杂度
递归函数满足 O(T) = a(T/b)+ O(n^c);master公式(具体可以在网上找)
上述是使用二分来完成查找对最大值的过程 所以b=2 如果分成4份来查找每份的最大值那么b=4。a的值为调用次数 这里是2 c的值为除去process(arr,L,mid); process(arr,mid+1,R);代码的时间复杂度 这里是常数项0
O(T) = 2(T/2)+ O(n^0);
log2^2 >0 所以时间复杂度为
O(N^log2) =O(N) 程序中的log2 就是以2为底