二分查找算法题

1.二分查找搜索算法(注意怎么和面试官描述你的思路)

  1. 最普通的二分查找(注意这里left<=right)

       int left = 0;

       int right = nums.length-1;

       while(left<=right){

         int mid = (left+right)/2;

         if(nums[mid]>target){

            right--;

         }else if(nums[mid]<target){

            left++; 

         }else{ 

            return mid;

         }

       }

  1. 寻找峰值(其实这里只需要根据题目要求,如果我想要的是满足条件的最后一个数,就是right = mid-1,如果是第一个数就是left= mid+1),注意如果是right = mid-1的话,mid = left+(right-left+1)/2;+1别忘了

  import java.util.*;

public class Solution {

    public int findPeakElement (int[] nums) {

       int left  = 0;

       int right  = nums.length-1;

       while(left<right){

          int mid = left+(right-left+1)/2;

          if(nums[mid]>nums[mid-1]){

            left = mid;

          }else{

            right = mid -1;

          }

       }

       return left;

    }

}

3.1旋转数组的最小值(顺序)--就是上课的套路

  public int findMin(int[] nums) {

       public int findMin(int[] nums) {

        int left = 0;

        int key = nums[0];

        int right = nums.length - 1;

        while (left < right) {

            int mid = left + (right - left) / 2;

            if (nums[mid] < key) {

                right = mid;

            } else {

                left = mid + 1;

            }

        }

        if (nums[left] >= key)

            return key;

        return nums[left];

    }

    }

3.2旋转数组的最小值(非降序)也就是存在不增不减和升序的情况(背就行)

public int minNumberInRotateArray (int[] nums) {

        if(nums.length==0){

            return 0;

        }

        int left = 0,right = nums.length-1;

        while(left<right){

            int mid =left+(right-left)/2;

            if(nums[mid]>nums[right]){

               left = mid+1;

            }else if(nums[mid]<nums[right]){

               right = mid;

            }else{

                right--;

            }

        }

        return nums[left];

    }

4.比较版本号

public int compare (String version1, String version2) {

        int n = version1.length();

        int m = version2.length();

        char[]s1 = version1.toCharArray();

        char[]s2 = version2.toCharArray();

        int i =0 , j =0 ;

        while(i<n&&j<m){

            int res1 = 0;

            int res2 = 0;

            while(i<n&&s1[i]!='.'){

                res1= res1*10 + (s1[i]-'0');

                i++;

            }

            while(j<m&&s2[j]!='.'){

                res2= res2*10 + (s2[j]-'0');

                j++;

            }

            if(res1>res2)

            return 1;

            else if(res1<res2)

            return -1;

            i++;

            j++;

        }

        while(i<m){

            int res11 = 0;

            while(i<m&&s1[i]!='.'){

               res11 = res11*10+(s1[i]-'0');

               i++;

            }

            if(res11>0)

              return 1;

            i++;

        }

           while(j<n){

            int res22 = 0;

           while(j<n&&s2[j]!='.'){

               res22 = res22*10+(s2[j]-'0');

               j++;

            }

            if(res22>0)

              return -1;

            j++;

         }

        return 0;

    }

  1. 逆序对

import java.util.*;

public class Solution {

    public int InversePairs (int[] nums) {

       return (int)mergeSort(nums,0,nums.length-1);

    }

    public long mergeSort(int[]nums,int left, int right){

        if(left>=right){

            return 0;

        }

        int mid = left+(right-left)/2;

        long ret = 0;

        ret+=  mergeSort(nums,left,mid);

        ret+=  mergeSort(nums,mid+1,right);

        int cur1 = left;

        int cur2 = mid+1;

        while(cur1<=mid){

           while(cur2<=right&&nums[cur2]>=nums[cur1]){

             cur2++;

           }

           if(cur2>right)

            break;

           ret+= right-cur2+1;

           cur1++;

        }

         cur1 = left;

         cur2 = mid+1;

         int[] tmp= new int[nums.length];

         int i = 0;

         while(cur1<=mid&&cur2<=right){

           if(nums[cur1]<nums[cur2]){

             tmp[i++] = nums[cur2++];

           }else{

             tmp[i++] = nums[cur1++];

           }

        }

         while(cur1<=mid){

            tmp[i++] = nums[cur1++];

         }

         while(cur2<=right){

            tmp[i++] = nums[cur2++];

         }

        for(int j = left;j<=right;j++){

            nums[j] = tmp[j-left];

        }

        return ret%1000000007;

    }

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值