LeetCode:719. 找出第 K 小的数对距离

2022-06-15  本文已影响0人  alex很累

问题链接

719. 找出第 K 小的数对距离

问题描述

数对 (a,b) 由整数 ab 组成,其数对距离定义为 ab 的绝对差值。

给你一个整数数组 nums 和一个整数 k ,数对由 nums[i]nums[j] 组成且满足 0 <= i < j < nums.length 。返回 所有数对距离中 第 k 小的数对距离。

提示:

示例

示例1
输入:nums = [1,3,1], k = 1
输出:0
解释:数对和对应的距离如下:
(1,3) -> 2
(1,1) -> 0
(3,1) -> 2
距离第 1 小的数对是 (1,1) ,距离为 0 。

示例2
输入:nums = [1,1,1], k = 2
输出:0

示例3
输入:nums = [1,6,1], k = 3
输出:5

解题思路

看一下提示的范围,就知道暴力破解直接没戏~
这道题,可以对数对距离的域值进行二分查找解题。

  1. 先对数组nums排序;
  2. 对数对距离的域值进行二分查找:
    A. 初始left为0,right为数组头尾相减的绝对值,middleleftright和的一半;
    B. 统计所有距离小于等于 middle 的数对数量,记为count
    C. 如果count大于等于kright = middle - 1;反之,left = middle + 1
    D. 如果left小于等于right,继续以上操作;
  3. left大于right时,返回结果left

代码示例(JAVA)

class Solution {
    public int smallestDistancePair(int[] nums, int k) {
        // 先进行排序
        Arrays.sort(nums);

        // 值域二分找k
        int length = nums.length;
        int left = 0, right = nums[length - 1] - nums[0];
        while (left <= right) {
            int middle = (right + left) / 2;
            int count = countPair(nums, middle);
            if (count >= k) {
                right = middle - 1 ;
            } else {
                left = middle + 1;
            }
        }

        return left;
    }

    // 统计数对
    public int countPair(int[] nums, int value) {
        int count = 0;
        for (int i = 0; i < nums.length - 1; i++) {
            for (int j = i + 1; j < nums.length; j++) {
                if (nums[j] - nums[i] <= value) {
                    count++;
                } else {
                    break;
                }
            }
        }

        return count;
    }
}

执行结果

上一篇下一篇

猜你喜欢

热点阅读