• LeetCode---Binary Search


    **475. Heaters
    思路:每趟循环查找离房子最近的热水器,计算距离,最后取最大距离
    
    public int findRadius(int[] houses, int[] heaters) {
        Arrays.sort(houses);
        Arrays.sort(heaters);
        
        int j = 0;
        int res = 0;
        for(int i = 0; i < houses.length; i++){
            //找离house[i]最近的heater
            while(j < heaters.length - 1 && heaters[j] + heaters[j + 1] <= 2 * houses[i]){
                j++;
            }
            res = Math.max(res,Math.abs(heaters[j] - houses[i]));
        }
        return res;
    }
    
    **410. Split Array Largest Sum
    思路:结果一定在最大值和总和之间,因此在这两个数之间用二分查找;看中间值能不能符合区间个数
    
    public int splitArray(int[] nums, int m) {
        int max = 0;
        int sum = 0;
        for(int i = 0; i < nums.length; i++){
            max = Math.max(max,nums[i]);
            sum += nums[i];
        }
        
        int i = max;
        int j = sum;
        while(i <= j){
            int d = i + (j - i) / 2;
            if(isValid(nums,m,d)) j = d - 1;
            else i = d + 1;
        }
        return i;
    }
    
    public boolean isValid(int[] nums,int m,int d){
        int count = 1;
        int total = 0;
        for(int i = 0; i < nums.length; i++){
            total += nums[i];
            if(total > d){
                total = nums[i];
                count++;
                if(count > m) return false;
            }
        }
        return true;
    } 
    
    **354. Russian Doll Envelopes
    思路:将区间按第一个数升序,第二个数降序排列,只需要计算第二个数的最长递增序列个数即可,注意Arrays.sort()的自定义排序的使用,即第300题
    
    public int maxEnvelopes(int[][] envelopes) {
        if(envelopes.length == 0 || envelopes[0].length == 0) return 0;
        Arrays.sort(envelopes,new Comparator<int[]>(){
            public int compare(int[] a,int[] b){
                if(a[0] == b[0]){
                    return b[1] - a[1];
                }
                else{
                    return a[0] - b[0]; 
                }
            }
        });
        
        int[] dp = new int[envelopes.length];
        for(int i = 0; i < dp.length; i++) dp[i] = 1; 
        for(int i = 1; i < envelopes.length; i++){
            for(int j = 0; j < i; j++){
                if(envelopes[i][1] > envelopes[j][1]) dp[i] = Math.max(dp[i],dp[j] + 1);
            }
        }
        int res = 0;
        for(int k : dp){
            res = Math.max(k,res);
        }
        return res;
    }
    
    总结
    278. First Bad Version:经典二分查找,属于查找临界点,注意最终终止索引
    374. Guess Number Higher or Lower:经典二分查找,属于查找某个数
    441. Arranging Coins:二分查找,属于查找临界点,注意最终终止索引
    367. Valid Perfect Square:二分查找,属于查找某个数
    240. Search a 2D Matrix II:从右上角开始查找,小则往下,大则往左
    378. Kth Smallest Element in a Sorted Matrix:将matrix放在PriorityQueue中实现排序
    392. Is Subsequence:按照s的顺序在t中查找,用计数器计数,等于s.length()则返回true
    69. Sqrt(x):二分查找,两个临界点m和m + 1,考虑所有区间的情况即可
    
    训练
    300. Longest Increasing Subsequence:dp中的元素表示当前索引值为序列最后一个数时的长度
    275. H-Index II:属于查找临界点,注意最终终止索引
    **436. Find Right Interval:用TreeMap,注意ceilingEntry()的使用
    50. Pow(x, n):递归但是要考虑减少栈帧,还有边界问题
    174. Dungeon Game:构造二维数组存每个格子所需最小体力,从终点开始一次往前计算所需最小体力,先计算边界
    
    提示
    1.直接查找某个数直接二分查找i <= j,并且最终一定能找到
    2.若是找某个临界点,也直接i <= j,只不过要想清楚最终终止索引的位置,相邻数中点一定是较小数,并且一定在临界点左边或就是临界点减小了范围
    3.若查找过程中判定条件会越界,则将int转化为long
  • 相关阅读:
    fail to start File System Check
    qemu:///system 没有连接驱动器可用;读取数据时进入文件终点: 输入/输出错误
    [转载]libvirt(virsh命令总结)
    【转载】CentOS 7自动以root身份登录gnome桌面 操作系统开机后自动登录到桌面 跳过GDM
    Linux查看PCIe版本及速率# lspci -vvv |grep Width -i
    JAVA的线程能够在多个CPU上执行么?
    给定字典做分词
    POJ 3130 &amp; ZOJ 2820 How I Mathematician Wonder What You Are!(半平面相交 多边形是否有核)
    高仿一元云购IOS应用源代码项目
    增加收藏兼容主流浏览器代码
  • 原文地址:https://www.cnblogs.com/LeonNew/p/6244200.html
Copyright © 2020-2023  润新知