【dp】E. Selling Souvenirs
http://codeforces.com/contest/808/problem/E
题意:给定n个重量为可能1,2,3的纪念品和各自的价值,问在背包总重量不超过m的条件下总价值最大为多少。
其中1 ≤ n ≤ 100000, 1 ≤ m ≤ 300000
首先可以想到的是重量相同的情况下,优先选择价值大的纪念品。所以我们可以把价值为1,2,3的纪念品分开,分别排序。
我们可以枚举重量为3的纪念品的个数为x,然后剩下的重量m-sum{3-elements}由1和2混合得出,这里可以动态规划预处理。
dp[i]是一个三元组{cost,cnt1,cnt2},分别表示重量为i的情况下的最大价值,以及这时候1和2分别用了多少。
dp[i]可以dp[i-1]和dp[i-2]推出。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#include<algorithm>
#include<cmath>
#include<set>
#include<map>
#include<utility>
using namespace std;
typedef long long ll;
const int maxn=3e5+; struct node
{
ll cost;
int cnt1;
int cnt2;
}dp[maxn];
ll sum[maxn];
ll a[maxn],b[maxn],c[maxn];
int n,m;
int main()
{
scanf("%d%d",&n,&m);
int weight;
ll cost;
int p=,q=,r=;
for(int i=;i<n;i++)
{
// scanf("%d%lld",&weight,&cost);
cin>>weight>>cost;
if(weight==)
{
a[p++]=cost;
}
else if(weight==)
{
b[q++]=cost;
}
else
{
c[r++]=cost;
}
}
sort(a,a+p);
sort(b,b+q);
sort(c,c+r);
dp[].cost=;
dp[].cnt1=p;
dp[].cnt2=q;
dp[].cost=a[p-];
dp[].cnt1=p-;
dp[].cnt2=q;
for(int i=;i<=m;i++)
{
if(dp[i-].cnt1->=&&dp[i-].cnt2->=)
{
if(dp[i-].cost+a[dp[i-].cnt1-]>dp[i-].cost+b[dp[i-].cnt2-])
{
dp[i].cost=dp[i-].cost+a[dp[i-].cnt1-];
dp[i].cnt1=dp[i-].cnt1-;
dp[i].cnt2=dp[i-].cnt2;
}
else
{
dp[i].cost=dp[i-].cost+b[dp[i-].cnt2-];
dp[i].cnt1=dp[i-].cnt1;
dp[i].cnt2=dp[i-].cnt2-;
}
}
else if(dp[i-].cnt1-<&&dp[i-].cnt2->=)
{
dp[i].cost=dp[i-].cost+b[dp[i-].cnt2-];
dp[i].cnt1=dp[i-].cnt1;
dp[i].cnt2=dp[i-].cnt2-;
}
else if(dp[i-].cnt1->=&&dp[i-].cnt2-<)
{
dp[i].cost=dp[i-].cost+a[dp[i-].cnt1-];
dp[i].cnt1=dp[i-].cnt1-;
dp[i].cnt2=dp[i-].cnt2;
}
else
{
break;
}
}
sum[r]=;
for(int i=r-;i>=;i--)
{
sum[i]=sum[i+]+c[i];
}
ll ans=;
for(int i=;i<=m;i++)
{
int x=(m-i)/;
ll temp=dp[i].cost+sum[max(r-x,)];
if(temp>ans)
{
ans=temp;
}
}
cout<<ans<<endl; return ;
}
注意一些小细节:
ll temp=dp[i].cost+sum[max(r-x,)];
重量为3的可能不够用
【dp】E. Selling Souvenirs的更多相关文章
- Kattis - honey【DP】
Kattis - honey[DP] 题意 有一只蜜蜂,在它的蜂房当中,蜂房是正六边形的,然后它要出去,但是它只能走N步,第N步的时候要回到起点,给出N, 求方案总数 思路 用DP 因为N == 14 ...
- HDOJ 1423 Greatest Common Increasing Subsequence 【DP】【最长公共上升子序列】
HDOJ 1423 Greatest Common Increasing Subsequence [DP][最长公共上升子序列] Time Limit: 2000/1000 MS (Java/Othe ...
- HDOJ 1501 Zipper 【DP】【DFS+剪枝】
HDOJ 1501 Zipper [DP][DFS+剪枝] Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Ja ...
- HDOJ 1257 最少拦截系统 【DP】
HDOJ 1257 最少拦截系统 [DP] Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Other ...
- HDOJ 1159 Common Subsequence【DP】
HDOJ 1159 Common Subsequence[DP] Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K ...
- HDOJ_1087_Super Jumping! Jumping! Jumping! 【DP】
HDOJ_1087_Super Jumping! Jumping! Jumping! [DP] Time Limit: 2000/1000 MS (Java/Others) Memory Limit: ...
- POJ_2533 Longest Ordered Subsequence【DP】【最长上升子序列】
POJ_2533 Longest Ordered Subsequence[DP][最长递增子序列] Longest Ordered Subsequence Time Limit: 2000MS Mem ...
- HackerRank - common-child【DP】
HackerRank - common-child[DP] 题意 给出两串长度相等的字符串,找出他们的最长公共子序列e 思路 字符串版的LCS AC代码 #include <iostream&g ...
- LeetCode:零钱兑换【322】【DP】
LeetCode:零钱兑换[322][DP] 题目描述 给定不同面额的硬币 coins 和一个总金额 amount.编写一个函数来计算可以凑成总金额所需的最少的硬币个数.如果没有任何一种硬币组合能组成 ...
随机推荐
- SonarQube+Svn+Jenkins环境搭建----问题总结
1.配置SVN后提示unable to access to repository,原因是使用的账户没有访问svn的权限,创建新的用户即可.注意新的用户,用户名,密码要跟svn上的权限一致. 创 ...
- android开发学习 ------- Retrofit+Rxjava+MVP网络请求的实例
http://www.jianshu.com/p/7b839b7c5884 推荐 ,照着这个敲完 , 测试成功 , 推荐大家都去看一下 . 下面贴一下我照着这个敲完的代码: Book实体类 - 用 ...
- ASP.NET Web API FilterAttribute假想
偶然的测试发现API FilterAttribute没用引用只会初始化一次 比如: 如果是 Global Action Filter, 则全局只会初始化一次 针对于不同的Controller级别的Ac ...
- css3纯手写loading效果
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...
- Java Web项目,Android和微信小程序的初始页面配置
Java Web项目 我们在Eclipse里开了Java Web项目之后,Run As Tomcat或者Apache服务器,本地运行,如果直接用http://localhost:8080访问项目,会发 ...
- makefile vpath变量
在讲vpath之前,我们首先了解以下makefile文件. 在类Unix系统中,当我们使用源码编译某个软件的时候,我们会使用confiure,make,make install这三个命令,其中cofi ...
- leetcode_41. First Missing Positive_cyclic swapping
https://leetcode.com/problems/first-missing-positive/ 给定一个长度为len的无序数组nums,找到其第一个丢失的正整数. 解法: 使用cyclic ...
- Python3基础教程(十六)—— 迭代器、生成器、装饰器
在这个实验里我们学习迭代器.生成器.装饰器有关知识. 这几个概念是 Python 中不容易理解透彻的概念,务必把所有的实验代码都完整的输入并理解清楚其中每一行的意思. 迭代器 Python 迭代器(I ...
- 【整理】 vue-cli 打包后显示favicon.ico小图标
vue-cli 打包后显示favicon.ico小图标 https://www.cnblogs.com/mmzuo-798/p/9285013.html
- 通过 getResources 找不到jar包中的资源和目录的解决方法
http://my.oschina.net/sub/blog/184074 今天碰到一个怪问题: 原本跑的好好的代码,打成 jar 包就不能运行了. 问题出在,代码中有一段自动扫描 classpath ...