力扣 2171. 拿出最少数目的魔法豆

GG_lyf

关注

阅读 36

2022-02-17

题目

给你一个 正 整数数组 beans ,其中每个整数表示一个袋子里装的魔法豆的数目。

请你从每个袋子中 拿出 一些豆子(也可以 不拿出),使得剩下的 非空 袋子中(即 至少 还有 一颗 魔法豆的袋子)魔法豆的数目 相等 。一旦魔法豆从袋子中取出,你不能将它放到任何其他的袋子中。

请你返回你需要拿出魔法豆的 最少数目。

示例

输入:beans = [4,1,6,5]
输出:4
解释:

  • 我们从有 1 个魔法豆的袋子中拿出 1 颗魔法豆。
    剩下袋子中魔法豆的数目为:[4,0,6,5]
  • 然后我们从有 6 个魔法豆的袋子中拿出 2 个魔法豆。
    剩下袋子中魔法豆的数目为:[4,0,4,5]
  • 然后我们从有 5 个魔法豆的袋子中拿出 1 个魔法豆。
    剩下袋子中魔法豆的数目为:[4,0,4,4]
    总共拿出了 1 + 2 + 1 = 4 个魔法豆,剩下非空袋子中魔法豆的数目相等。
    没有比取出 4 个魔法豆更少的方案。

输入:beans = [2,10,3,2]
输出:7
解释:

  • 我们从有 2 个魔法豆的其中一个袋子中拿出 2 个魔法豆。
    剩下袋子中魔法豆的数目为:[0,10,3,2]
  • 然后我们从另一个有 2 个魔法豆的袋子中拿出 2 个魔法豆。
    剩下袋子中魔法豆的数目为:[0,10,3,0]
  • 然后我们从有 3 个魔法豆的袋子中拿出 3 个魔法豆。
    剩下袋子中魔法豆的数目为:[0,10,0,0]
    总共拿出了 2 + 2 + 3 = 7 个魔法豆,剩下非空袋子中魔法豆的数目相等。
    没有比取出 7 个魔法豆更少的方案。

方法1:贪心

排序后预处理数组

Java实现1
class Solution {
    public long minimumRemoval(int[] beans) {
        int n = beans.length;
        Arrays.sort(beans);

        long[] left = new long[n];
        left[0] = 0;
        for (int i = 1; i < n; i++) {
            left[i] = left[i - 1] + beans[i - 1];
        }

        long[] right = new long[n];
        right[n - 1] = 0;
        for (int i = n - 2; i >= 0; i--) {
            right[i] = right[i + 1] + beans[i + 1];
        }

        long ans = Long.MAX_VALUE;
        for (int i = 0; i < n; i++) {
            long var = left[i] + right[i] - (n - i - 1) * (long)beans[i];
            ans = Math.min(var, ans);
        }

        return ans;
    }
}

在这里插入图片描述

Java实现2

在1的基础上改进

class Solution {
    public long minimumRemoval(int[] beans) {
        int n = beans.length;
        Arrays.sort(beans);
        long sum = 0;
        for (int i : beans) sum += i;

        long ans = Long.MAX_VALUE;
        for (int i = 0; i < n; i++) {
            long var = sum - (n - i) * (long)beans[i];
            ans = Math.min(var, ans);
        }

        return ans;
    }
}

在这里插入图片描述

精彩评论(0)

0 0 举报