C++:採用vector實現二分查詢及其變種總結
阿新 • • 發佈:2019-02-05
主要分為六種情況,閉區間,半開區間,中位值在迴圈之外的半開區間二分查詢首個序列,中位值在迴圈之外的半開區間二分查詢末尾序列,以及中位值在迴圈之外的完全開區間二分查詢首個序列和中位值在迴圈之外的完全開區間二分查詢末尾序列:
#include <iostream> #include <vector> #include <assert.h> using namespace std; // closed interval int binarySearchClose(vector<int> &invec, int &pos, int &value){ int low = 0, high = pos-1; assert(!invec.empty() && pos>=0); while(low <=high){ int mid = (low+high)/2; if(invec[mid] == value){ return mid; } else if(invec[mid] < value){ low = mid+1; } else{ high = mid-1; } } return -1; } // open interval int binarySearchOpen(vector<int> &invec, int &pos, int &value){ int low = 0, high = pos; while(low<high){ int mid = (low+high)/2; if(invec[mid] == value){ return mid; } else if(invec[mid] < value){ low = mid+1; } else{ // invec[mid] >= value high = mid; } } } // one improved binary search approach in open interval int binarySearchOpenImprovedFirst(vector<int> &invec, int &pos, int &value){ int low = 0, high = pos; assert(!invec.empty() && pos>=0); while(low<high){ int mid=(low+high)/2; // explain: status 1: when low position is moving, the high position is fixed. if(invec[mid]<value){ low = mid+1; } //status 2: when high position is moving, the low position is fixed. else{ // invec[mid] >= value high = mid; } } // the termination condition is high = low if(low>=pos || invec[low] != value){ return -low-1; } else{ return low; } } int binarySearchOpenImprovedLast(vector<int> &invec, int &pos, int &value){ int low = -1, high = pos-1; assert(!invec.empty() && pos >= 0); while(low<high){ //int mid = high - (high-low)/2; // int mid = (high+low)/2; int mid = (high+low+1)/2; // the above three value if(invec[mid]>value){ high = mid-1; } else{ low = mid; } } if(high<0 || invec[high] != value){ return -high-1; } else{ return high; } } // the complete open interval int binarySearchCompleteOpenFirst(vector<int> &invec, int &pos, int &value){ int low = -1, high = pos; assert(!invec.empty() || pos >= 0); while(low+1<high){ int mid = (low+high)/2; if(invec[mid] < value){ low=mid; } else{ // invec[mid] >=value high=mid; } } if(high>=pos || invec[high]!= value){ return -high-1; } else{ return high; // high = low+1 } } int binarySearchCompleteOpenLast(vector<int> &invec, int &pos, int &value){ int low = -1, high = pos; while(low+1<high){ int mid = (low+high)/2; if(invec[mid]>value){ high = mid; } else{ low = mid; } } if(low<0 || invec[low] != value){ return -1; } else{ return low; } } int main(){ vector<int> invec{1, 3, 3, 3, 3, 3, 3, 15, 19, 19, 19, 20, 20}; // len is 13 int len = invec.size(); int value = 20; //int pos = binarySearchClose(invec, len, value); // search in the closed interval, (when exist duplicate elements ), the find position is random //int pos = binarySearchOpen(invec, len, value); // search in the open interval, (when exist duplicate elements ), the find position is the last one //int pos = binarySearchOpenImprovedFirst(invec, len, value); // improved search approach in open interval region, (when exist duplicate elements ), the find position is the first one int pos = binarySearchOpenImprovedLast(invec, len, value); // improved search approach in open interval region, (when exist duplicate elements ), the find position is the last one // int pos = binarySearchCompleteOpenFirst(invec, len, value); // (when exist duplicate elements ), the find position is the first one //int pos = binarySearchCompleteOpenLast(invec, len, value); // (when exist duplicate elements ), the find position is the last one cout << "the position of the value is : " << pos << endl; }