第166場周賽實錄(變形二分法)

1281. 整數的各位積和之差

難度:簡單

給你一個整數 n,請你幫忙計算並返回該整數「各位數字之積」與「各位數字之和」的差。

示例 1:

輸入:n = 234
輸出:15
解釋:
各位數之積 = 2 * 3 * 4 = 24
各位數之和 = 2 + 3 + 4 = 9
結果 = 24 - 9 = 15

示例 2:

輸入:n = 4421
輸出:21
解釋:
各位數之積 = 4 * 4 * 2 * 1 = 32
各位數之和 = 4 + 4 + 2 + 1 = 11
結果 = 32 - 11 = 21

提示:

  • 1 <= n <= 10^5

解決方案:

class Solution:
    def subtractProductAndSum(self, n: int) -> int:
        multi = 1
        add = 0
        n_str = str(n)
        for i in n_str:
            multi = multi * int(i)
            add += int(i)
        return multi-add
執行用時 內存消耗 語言
32 ms 12.7 MB Python3

1282. 用戶分組

難度:中等

有 n 位用戶參加活動,他們的 ID 從 0 到 n - 1,每位用戶都 恰好 屬於某一用戶組。給你一個長度爲 n 的數組 groupSizes,其中包含每位用戶所處的用戶組的大小,請你返回用戶分組情況(存在的用戶組以及每個組中用戶的 ID)。

你可以任何順序返回解決方案,ID 的順序也不受限制。此外,題目給出的數據保證至少存在一種解決方案。

示例 1:

輸入:groupSizes = [3,3,3,3,3,1,3]
輸出:[[5],[0,1,2],[3,4,6]]
解釋:
其他可能的解決方案有 [[2,1,6],[5],[0,4,3]] 和 [[5],[0,6,2],[4,3,1]]。

示例 2:

輸入:groupSizes = [2,1,3,3,3,2]
輸出:[[1],[0,5],[2,3,4]]

提示:

  • groupSizes.length == n
  • 1 <= n <= 500
  • 1 <= groupSizes[i] <= n

解決方案:

class Solution:
    def groupThePeople(self, groupSizes: List[int]) -> List[List[int]]:
        ans = []
        res = dict()
        for i in range(len(groupSizes)):
            if not res.get(groupSizes[i]):
                res[groupSizes[i]] = [i]
            else:
                res[groupSizes[i]].append(i)
            if res.get(groupSizes[i]) and len(res[groupSizes[i]]) == groupSizes[i]:
                ans.append(res.pop(groupSizes[i]))
        return ans
執行用時 內存消耗 語言
88 ms 12.8 MB Python3

1283. 使結果不超過閾值的最小除數

難度:中等

給你一個整數數組 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

解決方案1:

import math
class Solution:
    def computer_sum(self, nums, d):
        ans = 0
        for i in nums:
            ans += math.ceil(i / d)
            # print(ans)
        return ans
    def smallestDivisor(self, nums, threshold):
        max_n = max(nums)
        min_n = 1
        mid = (max_n + min_n) // 2
        while mid != max_n and mid != min_n:
            if self.computer_sum(nums, mid) <= threshold:
                if self.computer_sum(nums, mid-1) > threshold:
                    return mid
                max_n = mid
                mid = (max_n + min_n) // 2
            else:
                min_n = mid
                mid = (min_n + max_n) // 2
        return mid
執行用時 內存消耗 語言
676 ms 18.2 MB Python3

解決方案2(來自網絡,簡化了上個方法):

class Solution:
    def smallestDivisor(self, nums: List[int], threshold: int) -> int:
        """
        簡單二分
        時間複雜度: nums.length*log(max(nums)) = 17*5*10^4
        :param nums:
        :param threshold:
        :return:
        """
        L, R = 1, max(nums)
        while (L < R):
            mid = (L + R) >> 1
            # 小於等於閾值, 說明 答案不是在mid的左邊就是mid
            if(sum(math.ceil(x/mid) for x in nums) <= threshold):
                R = mid
            # 大於閾值, 答案在mid右邊
            else:
                L = mid + 1
        return R
執行用時 內存消耗 語言
512 ms 18.2 MB Python3
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章