【中等】使数组互补的最少操作次数

在这里插入图片描述
在这里插入图片描述

本题不是纯粹的差分数组,只不过使用差分数组解决更快。
设一个数组res,其中res[x]表示的是,nums[i] + nums[n - 1 - i] 为 x 的时候,需要多少次操作。所以这题就抽象成计算出所有的x中最小的res[x]即可。关键是,如何求出每一个 res[x] 位置的值,需要多少操作?为了叙述方便,假设 nums[i] 为 A,nums[n - 1 - i] 为 B,最终的 A+B 为 C。
先假设res中所有数都是2,即都需要2次操作,然后在这上面进行筛选,注意这里的“所有数”表示范围[2, 2 * limit],因为nums[i] + nums[n - 1 - i] 最小是 2,即将两个数都修改为 1;最大是 2 * limit,即将两个数都修改成 limit
首先在区间[1 + min(A, B), limit + max(A, B)]中,res肯定都是1。这个区间表示的是某一个 A+B 的范围,A+B如果要等于这个区间中的一个数,只要修改一个A、B中的一个即可。
其次在[A + B]这个位置也要减1,很容易理解嘛,因为A和B要算出A+B根本不需要修改。
最后利用差分数组的方法求res中最小的一个。

class Solution {
public:
    int minMoves(vector<int>& nums, int limit) {
        vector<int> diff(2 * limit + 2, 0);
        int n = nums.size();
        for (int i = 0; i < n / 2; i++)
        {
            int A = nums[i], B = nums[n - 1 - i];
            //首先在区间[2, 2 * limit]中都是2
            int l = 2, r = 2 * limit;
            diff[l] += 2;
            diff[r + 1] -= 2;
            //在区间[1 + min(A, B), limit + max(A, B)]的都减去1
            l = 1 + min(A, B), r = limit + max(A, B);
            diff[l] += -1;
            diff[r + 1] -= -1;
            //用差分数组的方式把A+B的位置减去1
            l = A + B, r = A + B;
            diff[l] += -1;
            diff[r + 1] -= -1;
        }
        int ans = n, sum = 0;
        for (int i = 2; i < 2 * limit + 1; i++)
        {
            sum += diff[i];
            if (sum < ans)
                ans = sum;
        }
        return ans;
    }
};
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值