二分搜索的的使用不一定是在有序数组中查找使用,只要是一次条件筛选之后能过滤掉一半数据之后都可以使用
#include<iostream> #include<string> #include<stack>//pop,top,push #include<vector> using namespace std; class Solution { public: int getLessIndex(vector<int> arr) { if(arr.empty())//1.先判断是否为空 return -1; if(arr.size()==1||arr[0]<arr[1])//2.判断数组开头 return 0; if(arr[arr.size()-1]<arr[arr.size()-2])//3.判断数组结尾 return arr.size()-1; int low=1,high=arr.size()-2,mid; while(low<=high) { mid=low+(high-low)/2;//为了防止low+high过大导致溢出 if(arr[mid]>arr[mid-1])//从mid向左呈下降趋势,最小位置可能出现在mid左侧 high=mid-1; else if(arr[mid]>arr[mid+1])//从mid向右呈下降趋势,最小位置可能出现在mid右侧 low=mid+1; else//找到mid位置 return mid; } return -1; } }; int main() { int a[30]={10,5,10,5,0,1,2,4,7,3,2,9,5,4,6,5,10,6,7,10,9,4,3,7,2,9,5,4,6,10}; vector<int> arr(a,a+30); Solution s; cout<<s.getLessIndex(arr); return 0; }
#include<iostream> #include<string> #include<bitset>//pop,top,push #include<vector> #include<cmath> using namespace std; class QuickPower { public://https://www.cnblogs.com/Knuth/archive/2009/09/04/1559949.html int getPower(int k, int N) { if(k==0) return 0; if(N==0) return 1; if(k>1000000007) k=k%1000000007; //arr数组中的每个值对应k的二进制bit中的每一位 vector<long> arr; vector<int> bit; //把k拆分为二进制操作 long long m=N,temp=k,res; while(m) { arr.push_back(temp); temp*=temp; if(temp>1000000007) temp=temp%1000000007; if(m%2) bit.push_back(1); else bit.push_back(0); m=m/2; } for(int i=0,res=1;i<bit.size();i++) if(bit[i]) { res*=arr[i]; if(res>1000000007) res=res%1000000007; } return res%(1000000007); } }; int main() { QuickPower s; cout<<s.getPower(2,14876069); return 0; }
完全二叉树增加结点在树的最后一层从左到右依次添加,删除结点从右到左依次删除
找根节点的右子树的最左子树出现的位置,是否和左子树中的最左子节点出现在同一层
struct TreeNode { int val; struct TreeNode *left; struct TreeNode *right; TreeNode(int x) :val(x), left(NULL), right(NULL) {} }; class CountNodes { public: int count(TreeNode* root) { if(!root) return 0; int Lengthofleft=DepthofCom_Bitree((*root).left); int Lengthofright=DepthofCom_Bitree((*root).right); //深度为h的二叉树最多有2^h-1个结点(h>=1),最少有h个结点 if(Lengthofleft==Lengthofright) return pow(2.0,Lengthofleft)+count((*root).right); else return pow(2.0,Lengthofright)+count((*root).left); } int DepthofCom_Bitree(TreeNode *root) { if(!root) return 0; TreeNode *p=root; int len=0; while(p) { len++; p=(*p).left; } return len; } };
#include<iostream> #include<vector> using namespace std; class MinValue { public: int getMin(vector<int> arr, int n) { if(arr.empty()) exit(-1); if(n==1||arr[0]<arr[n-1])//整个数组是有序的 return arr[0]; int low=0,high=n-1,mid; while(low<high) { mid=low+(high-low)/2; if(arr[low]>arr[mid])//(升序数组)右半部分肯定移动到数组开头且最小值位于中间元素之前 6 5 1 2 3 4 high=mid; else if(arr[mid]>arr[high])//最小值位于中间元素之后 4 5 6 1 2 3 low=mid+1; else//arr[low]==arr[mid]==arr[high] 2 1 2 2 2 2 break; } if(low==high) return arr[low]; int min=arr[low]; while(low<=high) { if(arr[low]<min) min=arr[low]; low++; } return min; } }; int main() { int a[6]={4,5,6,1,2,3}; vector<int> arr(a,a+6); MinValue s; cout<<s.getMin(arr,6); return 0; }
#include<iostream> #include<vector> using namespace std; class LeftMostAppearance { public: int findPos(vector<int> arr, int n, int num) { if(!n) return -1; int low=0,high=n-1,mid; int res=-1; while(low<=high) { mid=low+(high-low)/2; if(arr[mid]<num) low=mid+1; else if(arr[mid]>num) high=mid-1; else { res=mid; high=mid-1; } } return res; } }; int main() { int a[5]={1,2,3,3,4}; vector<int> arr(a,a+5); LeftMostAppearance s; cout<<s.findPos(arr,5,3); return 0; }
#include<iostream> #include<vector> using namespace std; class Find { public: int findPos(vector<int> arr, int n) { if(arr.empty()||arr[0]>n-1||arr[n-1]<0) return -1; int res=-1; int low=0,high=n-1,mid=0; while(low<=high) { mid=low+(high-low)/2; if(arr[mid]<mid)//因为数组有序,所以左边的值都小于他的下标 low=mid+1; else if(arr[mid]>mid)//右边得值肯定也都大于他的下标 high=mid-1; else { res=mid; high=mid-1; } } return res; } }; int main() { int a[5]={-1,0,2,3}; vector<int> arr(a,a+4); Find s; cout<<s.findPos(arr,4); return 0; }