1283-使结果不超过阈值的最小除数

Raphael Liu Lv10

给你一个整数数组 nums 和一个正整数 threshold ,你需要选择一个正整数作为除数,然后将数组里每个数都除以它,并对除法结果求和。

请你找出能够使上述结果小于等于阈值 threshold 的除数中 最小 的那个。

每个数除以除数后都向上取整,比方说 7/3 = 3 , 10/2 = 5 。

题目保证一定有解。

示例 1:

**输入:** nums = [1,2,5,9], threshold = 6
**输出:** 5
**解释:** 如果除数为 1 ,我们可以得到和为 17 (1+2+5+9)。
如果除数为 4 ,我们可以得到和为 7 (1+1+2+3) 。如果除数为 5 ,和为 5 (1+1+1+2)。

示例 2:

**输入:** nums = [2,3,5,7,11], threshold = 11
**输出:** 3

示例 3:

**输入:** nums = [19], threshold = 5
**输出:** 4

提示:

  • 1 <= nums.length <= 5 * 10^4
  • 1 <= nums[i] <= 10^6
  • nums.length <= threshold <= 10^6

方法一:二分查找

假设我们选择了除数 d,当 d 增加时,正整数数组 nums 中的每个数 num[i] 除以 d 的结果 num[i] / d 单调递减,它们的和 total 同样也单调递减。

根据上述的单调性,我们就可以使用二分查找的方法,找出满足 total <= threshold 的最小除数 d。具体地,假设我们当前在二分查找的区间 [l, r] 中选择了除数 d',并计算出了对应的 total',此时会出现两种情况:

  • 如果 total' > threshold,那就说明我们选择的 d' 不满足要求。根据单调性,减小 d' 的值会增大 total' 的值,那么区间 [l, d'] 中不可能存在满足要求的除数,因此我们可以在区间 (d', r] 中继续进行二分查找。

  • 如果 total' <= threshold,那就说明我们选择的 d' 满足要求。由于题目中要求除数尽可能小,因此我们可以忽略区间 (d', r],而在区间 [l, d') 中继续进行二分查找。

这样我们就可以方便地使用二分查找得出最优解。

那么如何确定二分查找的上下限呢?显然,二分查找的下限是 1,这是最小的正整数。而二分查找的上限可以设置为数组 nums 中的最大值 M,这是因为当除数 d >= M 时,数组 nums 中的每个数除以 d 的结果均为 1total 的值恒等于数组 nums 的长度。由于题目中要求除数尽可能小,那么选择除数 d = M 一定比 d > M 更优。因此,将二分查找的上限设置为 M,可以保证不遗漏最优解。

[sol1]
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
class Solution {
public:
int smallestDivisor(vector<int>& nums, int threshold) {
int l = 1, r = *max_element(nums.begin(), nums.end());
int ans = -1;
while (l <= r) {
int mid = (l + r) / 2;
int total = 0;
for (int num: nums) {
total += (num - 1) / mid + 1;
}
if (total <= threshold) {
ans = mid;
r = mid - 1;
}
else {
l = mid + 1;
}
}
return ans;
}
};
[sol1]
1
2
3
4
5
6
7
8
9
10
11
12
class Solution:
def smallestDivisor(self, nums: List[int], threshold: int) -> int:
l, r, ans = 1, max(nums) + 1, -1
while l <= r:
mid = (l + r) // 2
total = sum((x - 1) // mid + 1 for x in nums)
if total <= threshold:
ans = mid
r = mid - 1
else:
l = mid + 1
return ans

复杂度分析

  • 时间复杂度:O(N\log C),其中 C 是一个常数,为二分查找的上下限之差。在本题给定的数据范围的限制下,C 不会超过 10^6。

  • 空间复杂度:O(1)。

 Comments
On this page
1283-使结果不超过阈值的最小除数