【力扣刷题】908. 最小差值 I

158 阅读1分钟

「这是我参与11月更文挑战的第 9 天,活动详情查看:2021最后一次更文挑战

原题链接

908. 最小差值 I - 力扣(LeetCode) (leetcode-cn.com)

题目描述

给你一个整数数组 nums,请你给数组中的每个元素 nums[i] 都加上一个任意数字 x (-k <= x <= k),从而得到一个新数组 result 。

返回数组 result 的最大值和最小值之间可能存在的最小差值。

测试用例

示例 1:

输入:nums = [0,10], k = 2
输出:6
解释:result = [2,8]

示例 2:

输入:nums = [1,3,6], k = 3
输出:0
解释:result = [3,3,3] or result = [4,4,4]

参数限制

  • 1 <= nums.length <= 10000
  • 0 <= nums[i] <= 10000
  • 0 <= k <= 10000

分析

在现有的数组上,为每一个数加上 [-k, k] 之间的值后,在新数组里找出最大最小项,计算他们的差值。在我们调整后每个数需要增加的最合适的值后,最大最小值的差值最小,题目大概是这么个意思,非常的绕

换个描述,在现有的数组上,找出他们的 max, min,算出差值 n,这个值是固定的。当在 [-k, k] 中分别选择两个数为 max, min 加上之后,他们的最小差值会是多少呢?

max-min > 2*k 时,这个最小的差值就是 2*k -(max-min)

max-min <= 2*k 时,这个最小差值就是 0

这道题最难的地方就是分析出上面两个公式

代码

最朴实的的方案,直接对数组进行升序排列,然后拿取开头的 min 结尾的 max,然后套公式返回值即可

var smallestRangeI = function(nums, k) {
    nums = nums.sort((a, b) => a - b);
    let diff = nums[nums.length - 1] - nums[0];
    return diff <= 2 * k ? 0 : diff - 2 * k;
};

优化

优化掉排序的操作,使用 2 个变量 max, min,遍历数组时对变量进行更新,结束遍历后数组的最大最小值就出来了,其余操作照旧

var smallestRangeI = function(nums, k) {
    let max = nums[0],
        min = max;
    nums.forEach(n => {
        if (n > max) {
            max = n;
        } else if (n < min) {
            min = n
        }
    })
    let diff = max - min;
    return diff <= 2 * k ? 0 : diff - 2 * k;
};

今天的力扣刷题就分享到这里,感谢大家的阅读~