Acwing 734. 能量石
贪心(微扰) + dp
这道题还是比较难的,前置知识:
算法1:暴力\(O(T * n! * n)\)
可以\(dfs\)全排列枚举所有吃的方案,然后每次线性算能量取最大值即可。
算法2:贪心 + dp \(O(T * n * \sum_{i = 1}^{n}s_i)\)
贪心将问题转化
发现有可能存在最优解的某些宝石的贡献为\(0\),我们剔除了这些宝石。
假设最优解的能量石排列长度为\(k (1 <= k <= n)\) 因为去掉了那些没有贡献的宝石,位置为:
\(a_1, a_2, a_3...a_k\)。
那么对于任意两个位置\(i = a_l, j = a_{l + 1} (1 <= l < k)\)
交换后两个宝石的贡献总和不会变得更大,即(假设之前的总时间为\(t\) ):
\(E_i - t * L_i + E_j - (t + S_i) * L_j >= E_j - t * L_j + E_i - (t + S_j) * L_i\)
整理后:
\(S_i * L_j <= S_j * L_i\)。
我们可以把跟\(i\)有关的放到一边,调整一下:
\(\frac{S_i}{L_i} <= \frac{S_j}{L_j}\)
这样,我们只要以如上条件作为宝石间排序的条件,进行一次\(sort\)。
因为对于其他形式的放置规律,必然可以通过交换满足\(\frac{S_i}{L_i} > \frac{S_j}{L_j}\)的相邻的两项来得到更小值。
那么最优解的坐标(新的坐标)一定满足:
\(a_i < a_2 < a_3 ... < a_k\)
dp
那么,我们只要搞个\(01\)背包,\(S_i\)作为费用,\(max(0, E_i - (t - S_i) * L_i)\) 作为价值 (\(t\)为当前花费时长)。
\(f[t]\) 表示当前正好花\(t\)时间得到的最大能量。
状态转移方程:
\(f[t] = max(f[t], f[t - S_i] + max(0, E_i - (t - S_i) * L_i))\)
由于我们背包放物品(宝石)的顺序是坐标从\(1\)到\(n\)的,所以一定能枚举到最优解。
初始状态:\(f[0] = 0\),其余为负无穷
答案:\(max(f[i]) (1 <= i <= \sum_{i = 1}^{n}s_i)\)
参考代码
#include <cstdio>
#include <iostream>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 105, S = 10005;
int n;
int f[S];
struct Node{
    int s, e, l;
    bool operator < (const Node &x) const{
        return s * x.l < x.s * l;
    }
}a[N];
int main() {
    int T, cnt = 0; scanf("%d", &T);
    while(T--) {
        memset(f, 0xcf, sizeof f);
        scanf("%d", &n);
        int t = 0;
        for(int i = 1, s, e, l; i <= n; i++) {
            scanf("%d%d%d", &s, &e, &l);
            t += s; a[i] = (Node) { s, e, l };
        }
        sort(a + 1, a + 1 + n);
        f[0] = 0;
        for(int i = 1; i <= n; i++) {
            for(int j = t; j >= a[i].s; j--)
                f[j] = max(f[j], f[j - a[i].s] + max(0, a[i].e - (j - a[i].s) * a[i].l));
        }
        int res = 0;
        for(int i = 1; i <= t; i++) res = max(res, f[i]);
        printf("Case #%d: %d\n", ++cnt, res);
    }
    return 0;
}
												
											Acwing 734. 能量石的更多相关文章
- AcWing 6. 多重背包问题 III
		
//f[i,j] 所有只从前i块能量石中选,且总体积恰好为j的方案数 #include <iostream> #include <algorithm> #include < ...
 - c++制作小游戏--雷电
		
用c++实现了一个小游戏--雷电,貌似执行的还不错.贴图和声效也是Duang!Duang!的.整个项目我也会给出下载链接,有兴趣的能够编译执行一下.用到了C++11的新特性,最好是使用vs2013编译 ...
 - [GDOI2016][树链剖分+主席树]疯狂动物城
		
题面 Description Nick 是只在动物城以坑蒙拐骗为生的狐狸,儿时受到偏见的伤害,放弃了自己的理想.他被兔子 Judy 设下圈套,被迫与她合作查案,而卷入意想不到的阴谋,历尽艰险后成为搭档 ...
 - 2019牛客暑期多校训练营(第七场)F-Energy stones(思维+树状数组)
		
>传送门< 题意:有n块能量石,每秒钟会增加Li的能量,但是一旦增长到了Ci它就不会增长了,它初始的能量为Ei. 现在有若干个时刻ti,会选择下标在[Si,Ti]的能量石吸取它们的能量,这 ...
 - 「Poetize10」能量获取
		
描述 Description “封印大典启动,请出Nescafe魂珠!”随着 圣主applepi一声令下,圣剑护法rainbow和魔杖护法freda将Nescafe魂珠放置于封印台上.封印台是一个树形 ...
 - <转>请戒掉成功学和正能量,那是麻痹人的毒药 | 新知
		
非常不幸的是,这将是一场非常糟糕的演说.我不想骗你们,你们从我这里几乎什么也学不到.你们在离开的时候肯定会感到失望,你们的生活并不会得到改善. 更糟糕的是,你还会意识到生活的本质毫无意义,你的一切努力 ...
 - AE插件:能量激光描边光效特效Saber Mac汉化版
		
与大家分享一款非常好用的AE插件Saber插件汉化版.videocopilot saber是一款能量激光描边光效特效AE插件,可以帮助用户制作出能量激光.传送门.霓虹灯.电流.光束.光剑等效果.小编现 ...
 - 英语chiltonite葡萄石chiltonite单词
		
葡萄石Chiltonite 1.葡萄石能够促进血液循环,具有美容养颜的功效,非常适合女性佩戴,可以增加个人魅力,还能加强事业财运,凝聚财富气场. 2.绿色光对应人体心轮,对心脏,肺脏有效用,内涵的磁石 ...
 - 区间DP小结 及例题分析:P1880 [NOI1995]石子合并,P1063 能量项链
		
区间类动态规划 一.基本概念 区间类动态规划是线性动态规划的拓展,它在分阶段划分问题时,与阶段中元素出现的顺序和由前一阶段的那些元素合并而来由很大的关系.例如状态f [ i ][ j ],它表示以已合 ...
 
随机推荐
- Exactly Once 语义
			
将服务器的 ACK 级别设置为-1,可以保证 Producer 到 Server 之间不会丢失数据,即 At Least Once 语义. 相对的,将服务器 ACK 级别设置为 0,可以保证生产者每条 ...
 - leetcode 30day--2
			
202. Happy Number Write an algorithm to determine if a number n is "happy". A happy number ...
 - TCP粘包问题的解决方案02——利用readline函数解决粘包问题
			
主要内容: 1.read,write 与 recv,send函数. recv函数只能用于套接口IO ssize_t recv(int sockfd,void * buff,size_t len,i ...
 - JVM全方位解读(附面试题)
			
java中就虚拟机是其他语言编写的(C语言+汇编语言,因此,JVM最常出现的攻击就是buffer overflow),如javac命令等,而java api是java写的,大多开源在openjdk,j ...
 - tcp黏包问题与udp为什么不黏包
			
1.先说下subprocess模块的用法,为了举个黏包的例子 # 通过一个例子 来认识网络编程中的一个重要的概念 # 所有的客户端执行server端下发的指令,执行完毕后,客户端将执行结果给返回给服务 ...
 - MySQL 四种隔离级别详解,看完吊打面试官
			
转发链接:https://zhuanlan.zhihu.com/p/76743929 什么是事务 事务是应用程序中一系列严密的操作,所有操作必须成功完成,否则在每个操作中所作的所有更改都会被撤消.也就 ...
 - 面试大厂必看!就凭借这份Java多线程和并发面试题,我拿到了字节和美团的offer!
			
最近好多粉丝私信我说在最近的面试中老是被问到多线程和高并发的问题,又对这一块不是很了解,很简单就被面试官给问倒了,被问倒的后果当然就是被刷下去了,因为粉丝要求,我最近也是花了两天时间 给大家整理了这一 ...
 - 新鲜出炉!春招-面试-阿里钉钉、头条广告,美团面经分享,看我如何拿下offer!
			
之前给大家分享了一个朋友在字节面试的面试经历和拿到offer的过程,过程也算是比较精彩了,感兴趣的朋友可以去翻翻之前的那篇文章.话不多说重点来啦,一直有人发私信问我有没有其他大厂的面经分享啊,我也是联 ...
 - 二叉堆python实现
			
二叉堆是一种完全二叉树,我们可以使用列表来方便存储,也就是说,用列表将树的所有节点存储起来. 如下图,是小根堆方式的二叉堆,假设父节点的下标为p,则他的左孩子下标为2P+1,右孩子下标为2P+2 cl ...
 - 使用Camtasia制作冰雪奇缘视频
			
冰雪奇缘的精良制作,以及场景的华丽,让很多女孩子都很喜欢.对于其中美丽的冰雪场景,我们还可以使用Camtasia(Windows系统)教程录制软件来做冰雪奇缘视频. Camtasia教程录制软件是一款 ...