<每日一刷>大厂面试必备

目录

题目:

概述:

提示:

本人解答(java):

官方解答:

方法:排序 + 贪心

提示 1

提示 2

Java代码:

C++代码:

go代码:

python代码:

来源:


题目:

        数组中最大数对和的最小值

概述:

一个数对 (a,b) 的 数对和 等于 a + b 。最大数对和 是一个数对数组中最大的 数对和

  • 比方说,如果我们有数对 (1,5) ,(2,3) 和 (4,4),最大数对和 为 max(1+5, 2+3, 4+4) = max(6, 5, 8) = 8 。

给你一个长度为 偶数 n 的数组 nums ,请你将 nums 中的元素分成 n / 2 个数对,使得:

  • nums 中每个元素 恰好 在 一个 数对中,且
  • 最大数对和 的值 最小 。

请你在最优数对划分的方案下,返回最小的 最大数对和 。

示例 1:

输入:nums = [3,5,2,3]
输出:7
解释:数组中的元素可以分为数对 (3,3) 和 (5,2) 。
最大数对和为 max(3+3, 5+2) = max(6, 7) = 7 。

示例 2:

输入:nums = [3,5,4,2,4,6]
输出:8
解释:数组中的元素可以分为数对 (3,5),(4,4) 和 (6,2) 。
最大数对和为 max(3+5, 4+4, 6+2) = max(8, 8, 8) = 8 。
 

提示:

  • n == nums.length
  • 2 <= n <= 105
  • n 是 偶数 。
  • 1 <= nums[i] <= 105

本人解答(java):

class Solution {
    public int minPairSum(int[] nums) {

        Arrays.sort(nums);
        int len = nums.length;
        int left = 0, right = len - 1;
        int ans = 0;
        while (left < right) {
            ans = Math.max(nums[left++] + nums[right--], ans);
        }
        return ans;
    }
}

官方解答:

方法:排序 + 贪心
提示 1

数组内只有两个数的情况是平凡的。我们可以考虑数组中只有四个数x1

≤ x2 ≤ x3 ≤ x4 的情况。此时 (x1, x4), (x2, x3) 的拆分方法对应的最大数对和一定是最小的。

提示 1 解释

我们可以枚举所有的拆分方法。除了上文的拆分方法外还有两种拆分方法:

  • (x1,x3) , (x2,x4)

        此时x2+x4 ≥ x1+x4且x2+x4 ≥x2+x3。

        那么max(x1+x3 , x2+x4) ≥ x2+x4 ≥ max(x1+x4,x2+x3)。

  • (x1,x2) , (x3,x4)

        同样的,max(x1+x2 , x3+x4) ≥ x3+x4 ≥ max(x1+x4 , x2+x3)。

提示 2

对于 n 个数(n 为偶数)的情况,上述的条件对应的拆分方法,即第 k 大与第 k 小组成的 n/2 个数对,同样可以使得最大数对和最小。

提示 2 解释

我们可以类似 提示 1 对所有数建立全序关系,即X1 ≤ …… ≤ Xn​。我们需要证明,任意的拆分方法得到的最大数对和一定大于等于给定的拆分方法得到的最大数对和。

我们可以考虑上述命题的充分条件:假设给定拆分方法中的数对和Xk+Xn+1-k在k=k' 时最大,那么对于任意的拆分方法,都存在一组 u, v使得 Xu+Xv ≥ Xk'+Xn+1-k'。

我们可以用反证法证明。

同样,我们假设 u < v,那么使得Xv ≥ Xn+1-k'的 v 的取值一共有 k'种。即闭区间[n+1-k',n]

中的所有整数。对于这些 v 组成的数对,如果想使得 Xu + Xv < Xk' + Xn+1-k' 恒成立,必须要 Xu < Xk'。此时需要有 k'个不同的 u 的取值,但只有闭区间 [1,k'-1]中的 k'-1 个整数满足Xu < Xk'的条件,这就产生了矛盾。

因此,一定存在一组 u, v 使得Xu+Xv ≥ Xk'+Xn+1-k'。

思路与算法

根据 提示 2,我们需要将 nums 排序。排序后,我们遍历每一个第 k 大与第 k 小组成的数对,计算它们的和,并维护这些和的最大值。同样根据 提示 2,遍历完成后求得的最大数对和就是满足要求的最小值。

C代码:

int cmp(int *a, int *b) {
    return *a - *b;
}

int minPairSum(int *nums, int numsSize) {
    int res = 0;
    qsort(nums, numsSize, sizeof(int), cmp);
    for (int i = 0; i < numsSize / 2; ++i) {
        res = fmax(res, nums[i] + nums[numsSize - 1 - i]);
    }
    return res;
}

Java代码:

class Solution {
    public int minPairSum(int[] nums) {
        int n = nums.length;
        int res = 0;
        Arrays.sort(nums);
        for (int i = 0; i < n / 2; ++i) {
            res = Math.max(res, nums[i] + nums[n - 1 - i]);
        }
        return res;
    }
}

C++代码:

class Solution {
public:
    int minPairSum(vector<int>& nums) {
        int n = nums.size();
        int res = 0;
        sort(nums.begin(), nums.end());
        for (int i = 0; i < n / 2; ++i) {
            res = max(res, nums[i] + nums[n - 1 - i]);
        }
        return res;
    }
};

go代码:

func minPairSum(nums []int) (ans int) {
    sort.Ints(nums)
    n := len(nums)
    for i, val := range nums[:n/2] {
        ans = max(ans, val+nums[n-1-i])
    }
    return
}

func max(a, b int) int {
    if a > b {
        return a
    }
    return b
}

python代码:

class Solution:
    def minPairSum(self, nums: List[int]) -> int:
        n = len(nums)
        res = 0
        nums.sort()
        for i in range(n // 2):
            res = max(res, nums[i] + nums[n-1-i])
        return res

来源:

力扣(LeetCode)
链接:

https://leetcode-cn.com/problems/minimize-maximum-pair-sum-in-array
 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

黄辛华

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值