POJ1821 Fence
题意
| Time Limit: 1000MS | Memory Limit: 30000K | |
| Total Submissions: 6478 | Accepted: 2129 |
Description
Being the team's leader you want to determine for each worker the interval that he should paint, knowing that the total income should be maximal. The total income represents the sum of the workers personal income.
Write a program that determines the total maximal income obtained by the K workers.
Input
Input
N K
L1 P1 S1
L2 P2 S2
...
LK PK SK
Semnification
N -the number of the planks; K ? the number of the workers
Li -the maximal number of planks that can be painted by worker i
Pi -the sum received by worker i for a painted plank
Si -the plank in front of which sits the worker i
Output
Sample Input
8 4
3 2 2
3 2 3
3 3 5
1 1 7
Sample Output
17
Hint
the worker 1 paints the interval [1, 2];
the worker 2 paints the interval [3, 4];
the worker 3 paints the interval [5, 7];
the worker 4 does not paint any plank
Source
K个人对N块木板涂色,每个人初始站在一块木板前(不重复),每人最多只能涂包含所站木板的连续l个木板或一个木板也不涂。给出每人最多涂的木块数l,涂一快木板的工钱p,站的木板s。求这群人最多共获得多少工钱。
分析
参照mousehao001的题解。
dp[i][j]表示前i个人对前j块木板操作的最大收益。
核心状态转移方程:
dp[i][j]=max(dp[i][j-1],dp[i-1][k]+P[i].p*(j-k),dp[i-1][j])
max(0,P[i].s-P[i].l)<=k<min(P[i].s-1,j) k=0表示前i-1个人在玩泥巴。。
显然直接做就是枚举i,j,k。
观察dp[i-1][k]+P[i].p*(j-k)=(dp[i-1][k]-P[i].p*k)+P[i].p*j
在枚举k的时候,P[i].p*j的值已经确定不用考虑,只需要找出使(dp[i-1][k]-P[i].p*k)最大的k就行了,又观察到这个式子的值不与j相关,也就是说在枚举k之前我们就可以通过某种方法找出这个k,即:构造递减的 单调队列 维护k值。
时间复杂度\(O(MN)\)
代码
#include<iostream>
#include<algorithm>
#define rg register
#define il inline
#define co const
template<class T>il T read(){
rg T data=0,w=1;rg char ch=getchar();
while(!isdigit(ch)) {if(ch=='-') w=-1;ch=getchar();}
while(isdigit(ch)) data=data*10+ch-'0',ch=getchar();
return data*w;
}
template<class T>il T read(rg T&x) {return x=read<T>();}
typedef long long ll;
using namespace std;
co int N=16001,M=101;
struct rec{int L,P,S;}a[M];
bool operator<(co rec&a,co rec&b) {return a.S<b.S;}
int n,m,f[M][N],q[N];
int calc(int i,int k){
return f[i-1][k]-a[i].P*k;
}
int main(){
read(n),read(m);
for(int i=1;i<=m;++i) read(a[i].L),read(a[i].P),read(a[i].S);
sort(a+1,a+m+1);
for(int i=1;i<=m;++i){
int l=1,r=0;
for(int k=max(0,a[i].S-a[i].L);k<=a[i].S-1;++k){
while(l<=r&&calc(i,q[r])<=calc(i,k)) --r;
q[++r]=k;
}
for(int j=1;j<=n;++j){
f[i][j]=max(f[i-1][j],f[i][j-1]);
if(j>=a[i].S){
while(l<=r&&q[l]<j-a[i].L) ++l;
if(l<=r) f[i][j]=max(f[i][j],calc(i,q[l])+a[i].P*j);
}
}
}
printf("%d\n",f[m][n]);
return 0;
}
POJ1821 Fence的更多相关文章
- [POJ1821]Fence(单调队列优化dp)
[poj1821]Fence 有 N 块木板从左至右排成一行,有 M 个工匠对这些木板进行粉刷,每块木板至多被粉刷一次.第 i 个工匠要么不粉刷,要么粉刷包含木板 Si 的,长度不超过Li 的连续一段 ...
- poj1821 Fence【队列优化线性DP】
Fence Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 6122 Accepted: 1972 Description ...
- POJ1821 Fence 题解报告
传送门 1 题目描述 A team of $k (1 <= K <= 100) $workers should paint a fence which contains \(N (1 &l ...
- poj1821 Fence(单调队列优化dp)
地址 一排N个木板,M个工匠站在不同位置$S_i$,每个人可以粉刷覆盖他位置的.最长长度为$L_i$木板段,每刷一个有$P_i$报酬.同一木板只刷一次.求最大报酬. 根据每个人的位置dp,设$f[i] ...
- $Poj1821\ Fence\ $单调队列优化$DP$
Poj Acwing Description 有N块木板等待被M个工匠粉刷,每块木板至多被刷一次.第i个工匠要么不粉刷,要么粉刷包含木块Si的,长度不超过Li的连续的一段木板,每粉刷一块可以得到P ...
- poj1821 Fence(dp,单调队列优化)
题意: 由k(1 <= K <= 100)个工人组成的团队应油漆围墙,其中包含N(1 <= N <= 16 000)个从左到右从1到N编号的木板.每个工人i(1 <= i ...
- poj1821——Fence
题意: 一个栅栏一共有n(从1--n)个木板,我们找k个工人去粉刷它,li表示每个人有限制粉刷木板数量,pi表示粉刷一个木板得到的钱,si表示他开始在那个木板前面 如果一个工人要粉刷,那么他必须粉刷s ...
- 单调队列与DP
算是一个总结吧! 先来一个模板: TYVJ 1305 最大子序和 题目描述 输入一个长度为n的整数序列,从中找出一段不超过M的连续子序列,使得整个序列的和最大. 例如 1,-3,5,1,-2,3 当m ...
- Fence(poj1821)
Fence Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 4705 Accepted: 1489 Description ...
随机推荐
- C# ToLookup
下文参考翻译自: C#/.NET Little Wonders: The ToLookup() LINQ Extension Method 故事的背景 让我们先来创建一个简单的类来表示产品,产品有ID ...
- C# 图片缩略图
/// <summary> /// 生成缩略图 /// </summary> /// <param name="sourceFile">原始图片 ...
- ubuntu1404安装搜狗输入法
1.安装fcitx,一种输入法框架 apt-get install fcitx 2.配置使用fcitx 配置中心-语言支持-键盘输入方式系统,选择fcitx 3.登出再登入 4.下载sougou安装d ...
- 原生JS获取DOM 节点到浏览器顶部的距离或者左侧的距离
关于js获取dom 节点到浏览器顶/左部的距离,Jquery里面有封装好的offset().top/offset().left,只到父级的顶/左部距离position().top/position() ...
- [hdu P4081] Qin Shi Huang’s National Road System
[hdu P4081] Qin Shi Huang’s National Road System Time Limit: 2000/1000 MS (Java/Others) Memory Li ...
- lumion的基本操作,天气系统,景观系统。5.25
1.打开场景,按住鼠标右键可以选择方向. 2.向前移动:W,向后移动S,亦可以用鼠标滚轮向前或者向后滚.向左A向右D, 3.Q提升视角,E下降视角. 4.鼠标滚轮点下去,进行提升和下降视角.左右移动, ...
- 跟随我在oracle学习php(5)
框架(把一个页面引入当前页面 易维护 扩展 复用)<iframe src=”” frameborder=“”> 格式:iframe <frameset> <frame&g ...
- Centos7配置TiDB集群
一:各模块属性 模块名称 状态 建议实例数 功能 负载均衡组件 TiDB 无状态 2 接收SQL请求,处理SQL相关逻辑,并通过PB找到存储数据的TiKV地址 LVS.HAProxy.F5 PB 集群 ...
- Linux磁盘挂载
mount命令 用于加载文件系统到指定的加载点.此命令的最常用于挂载cdrom,使我们可以访问cdrom中的数据,因为你将光盘插入cdrom中,Linux并不会自动挂载,必须使用Lin ...
- scikit-learn实现简单的决策树
#encoding=utf-8import numpy as npimport pandas as pd def main(): #Pre-processing from sklearn.datase ...