首页 > 其他分享 >LeetCode 1049. 最后一块石头的重量 II

LeetCode 1049. 最后一块石头的重量 II

时间:2023-05-05 14:11:39浏览次数:45  
标签:stones int 1049 石头 II 最小值 sum 代数 LeetCode

思路

  • 任何时刻,某个石头的重量永远都是若干石头加减运算的绝对值
    • a-b+c
    • 合并石头都是减法,但仍可能出现+运算符,如 a-(b-c)=a-b+c
  • 任何一种合并方法,最后一个石头的重量都可以表示成一种代数形式,如 a+b-c+d+e+f-g
    • 不是所有的代数形式都可以转换为一种合并方法,如 a+b+c
  • 因此题目要求的就是形如 a-b-c+d+e+f-g... 的最小值
    • 可以表示成合并方法的代数形式所有代数形式的子集,如果代数形式的最小值位于子集中那么所有代数形式的最小值一定也是子集的最小值
  • 将原问题看作,挑选若干石头作为正项和负项,使得正负项之和绝对值之差最小
    • S正 为正项和,S负 为负项和,S 为所有石头重量和,min(S负-S正)=min(S-2*S正)=S-2*S正(max),且S正≤S总/2
    • 这里默认正项和小于负项和(如果不是加个负号即可,不影响绝对值)
  • 进而将题目看作 01 背包,背包体积为 S/2,挑选若干石头作为正项,使得 S 正最大
class Solution {
public:
    int f[35][3010];//f[i][j]表示选前i个物品,体积不超过j的最大价值
    int lastStoneWeightII(vector<int>& stones) {
        int n=stones.size(),sum=0;
        for(auto i:stones)  sum+=i;
        for(int i=1;i<=n;i++)
            for(int j=0;j<=sum/2;j++)
            {
                f[i][j]=f[i-1][j];
                if(j>=stones[i-1])    
                    f[i][j]=max(f[i][j],f[i-1][j-stones[i-1]]+stones[i-1]);
            }
        return sum-2*f[n][sum/2];
    }
};

标签:stones,int,1049,石头,II,最小值,sum,代数,LeetCode
From: https://www.cnblogs.com/tangxibomb/p/17373956.html

相关文章

  • [Leetcode] 0697.数组的度
    697.数组的度点击上方标题跳转至leetcode题目描述给定一个非空且只包含非负数的整数数组 nums,数组的度的定义是指数组里任一元素出现频数的最大值。你的任务是在nums中找到与 nums 拥有相同大小的度的最短连续子数组,返回其长度。 示例1:输入:nums=[1,2,2,3,1]输......
  • AcWing 754. 平方矩阵 II
    AcWing754.平方矩阵II1.地址https://www.acwing.com/problem/content/756/2.题解#include<iostream>#include<cstdio>#include<cmath>usingnamespacestd;//每个元素的值为:各个元素下标相减的绝对值+1intmain(){intmatrix[102][102];intn;......
  • 一个stm23移植u8g2驱动iic屏SSD1306方案12864的左边竖着两列没有显示的奇怪问题
    初始化后画一个方框u8g2_DrawLine(&u8g2,0,0,127,0);u8g2_DrawLine(&u8g2,1,0,1,63);//左边框u8g2_DrawLine(&u8g2,0,63,127,63);u8g2_DrawLine(&u8g2,127,0,127,63);左边框地址为0不显示,设置为1还是不显示设置为2可以看到竖线了中景园......
  • LeetCode 416 分割等和子集
    LeetCode|416.分割等和子集给你一个只包含正整数的非空数组 nums。请你判断是否可以将这个数组分割成两个子集,使得两个子集的元素和相等。示例1:输入:nums=[1,5,11,5]输出:true解释:数组可以分割成[1,5,5]和[11]。示例2:输入:nums=[1,2,3,5]输出:false解......
  • [Leetcode] 0693. 交替位二进制数
    693.交替位二进制数点击上方标题跳转至leetcode题目描述给定一个正整数,检查它的二进制表示是否总是0、1交替出现:换句话说,就是二进制表示中相邻两位的数字永不相同。 示例1:输入:n=5输出:true解释:5的二进制表示是:101示例2:输入:n=7输出:false解释:7的二进制表示......
  • [Leetcode] 0696. 计数二进制子串
    696.计数二进制子串点击上方链接跳转至leetcode题目描述给定一个字符串 s,统计并返回具有相同数量0和1的非空(连续)子字符串的数量,并且这些子字符串中的所有0和所有1都是成组连续的。重复出现(不同位置)的子串也要统计它们出现的次数。 示例1:输入:s="00110011"输......
  • [Leetcode] 0674. 最长连续递增序列
    674.最长连续递增序列题目描述给定一个未经排序的整数数组,找到最长且连续递增的子序列,并返回该序列的长度。连续递增的子序列可以由两个下标l和r(l<r)确定,如果对于每个l<=i<r,都有nums[i]<nums[i+1],那么子序列[nums[l],nums[l+1],...,nums[r-1],nums[......
  • [Leetcode] 0680. 验证回文串 II
    680.验证回文串II点击上方标题跳转至leetcode题目描述给你一个字符串 s,最多可以从中删除一个字符。请你判断s是否能成为回文字符串:如果能,返回true;否则,返回false。 示例1:输入:s="aba"输出:true示例2:输入:s="abca"输出:true解释:你可以删除字符'c'。示......
  • [Leetcode] 0661. 图片平滑器
    661.图片平滑器题目描述图像平滑器是大小为 3x3的过滤器,用于对图像的每个单元格平滑处理,平滑处理后单元格的值为该单元格的平均灰度。每个单元格的 平均灰度定义为:该单元格自身及其周围的8个单元格的平均值,结果需向下取整。(即,需要计算蓝色平滑器中9个单元格的平均......
  • cpp: Strategy Pattern II
     //Gold.h:此文件包含"Gold"类。策略模式StrategyPatternC++14//2023年5月1日涂聚文GeovinDuVisualStudio2022edit.#pragmaonce//#ifndefGOLD_H//#defineGOLD_H#ifndef_GOLD_#define_GOLD_#include<iostream>#include<sstrea......