P2885 [USACO07NOV]电话线Telephone Wire

给出若干棵树的高度,你可以进行一种操作:把某棵树增高h,花费为h*h。

操作完成后连线,两棵树间花费为高度差*定值c。

求两种花费加和最小值。

输入输出样例

输入 #1复制

5 2
2
3
5
1
4
输出 #1复制

15

sol:显然暴力的dp很容易得到,dp[i][j]表示第i个高度为j个最小代价
#include <bits/stdc++.h>
using namespace std;
typedef int ll;
inline ll read()
{
ll S=; char ch=' '; bool f=;
while(!isdigit(ch)) {f|=(ch=='-'); ch=getchar();}
while(isdigit(ch)) {S=(S<<)+(S<<)+(ch-''); ch=getchar();}
return (f)?(-S):(S);
}
#define R(x) x=read()
inline void write(ll x)
{
if(x<) {putchar('-'); x=-x;}
if(x<) {putchar(x+''); return;}
write(x/); putchar(x%+'');
}
#define W(x) write(x),putchar(' ')
#define Wl(x) write(x),putchar('\n')
const int N=,M=,inf=0x3f3f3f3f;
int n,c,hig[N],mx,ans;
int dp[N][M];
inline int sqr(int x){return x*x;}
int main()
{
freopen("luogu2885_data.in","r",stdin);
int i,j,k;
R(n); R(c);
for(i=;i<=n;i++)
{
R(hig[i]); mx=max(mx,hig[i]);
}
memset(dp,,sizeof dp);
dp[][hig[]]=;
for(i=;i<=mx-hig[];i++) dp[][hig[]+i]=i*i;
for(i=;i<=n;i++)
{
for(j=hig[i];j<=mx;j++) for(k=hig[i-];k<=mx;k++)
{
dp[i][j]=min(dp[i][j],dp[i-][k]+sqr(j-hig[i])+c*abs(j-k));
}
}
ans=inf;
for(i=hig[n];i<=mx;i++) ans=min(ans,dp[n][i]);
Wl(ans);
return ;
}

然后发现容易拆开abs分类讨论一下即可

#include <bits/stdc++.h>
using namespace std;
typedef int ll;
inline ll read()
{
ll s=; bool f=; char ch=' ';
while(!isdigit(ch)) {f|=(ch=='-'); ch=getchar();}
while(isdigit(ch)) {s=(s<<)+(s<<)+(ch^); ch=getchar();}
return (f)?(-s):(s);
}
#define R(x) x=read()
inline void write(ll x)
{
if(x<) {putchar('-'); x=-x;}
if(x<) {putchar(x+''); return;}
write(x/); putchar((x%)+'');
}
#define W(x) write(x),putchar(' ')
#define Wl(x) write(x),putchar('\n')
const int N=,inf=0x3f3f3f3f;
int n,c,mx,hig[N];
int dp[N][],mn[];
inline int sqr(int x){return x*x;}
int main()
{
freopen("luogu2885_data.in","r",stdin);
int i,j;
R(n); R(c);
for(i=;i<=n;i++) mx=max(mx,hig[i]=read());
memset(dp,,sizeof dp);
for(i=hig[];i<=mx;i++) dp[][i]=sqr(i-hig[]);
for(i=;i<=n;i++)
{
for(j=;j<=hig[i-]-;j++) mn[j]=inf;
for(j=hig[i-];j<=mx;j++) mn[j]=min(mn[j-],dp[i-][j]-c*j);
for(j=hig[i];j<=mx;j++) dp[i][j]=min(dp[i][j],mn[j]+sqr(j-hig[i])+c*j);
mn[mx+]=inf;
for(j=mx;j>=hig[i-];j--) mn[j]=min(mn[j+],dp[i-][j]+c*j);
for(j=hig[i-]-;j>=;j--) mn[j]=mn[hig[i-]];
for(j=hig[i];j<=mx;j++) dp[i][j]=min(dp[i][j],mn[j]+sqr(j-hig[i])-c*j);
// for(j=hig[i];j<=mx;j++) cout<<i<<' '<<j<<' '<<dp[i][j]<<endl; putchar('\n');
}
int ans=inf;
for(j=hig[n];j<=mx;j++) ans=min(ans,dp[n][j]);
Wl(ans);
return ;
}

ac

 

luogu2885的更多相关文章

随机推荐

  1. poj 3617 弱鸡贪心

    比赛的时候扣了一道贪心的题目,不会写,,现在补一补一些基础的贪心. 题意:给定一个字符串s,要求按下列操作生成一个新串t--每次从s串中的最前和最后取一个字符给t,要求生成的t字典序最小. 题解:由于 ...

  2. Spring Boot 多个域名指向同一IP

    一.需求:直接通过域名访问首页(同一应用下,多个首页,包括PC端.手机端首页) 方法:采用多个域名绑定同一IP下同一应用,不同域名对应不同产品(PC.手机端)的方法,在后台通过拦截器判断 reques ...

  3. Abp 领域事件简单实践 <三> 自定义事件

    熵片用到的  EntityCreatedEventData<TEntity>,继承自EventData. 我们可以自定义事件: public class TestEvent: EventD ...

  4. Asp.Net Core 轻松学系列-4玩转配置文件

    目录 前言 另类方式使用 hosting.json 使程序运行于多个端口 结语 前言     在 .NET Core 项目中,配置文件有着举足轻重的地位:与.NetFramework 不同的是,.NE ...

  5. IOC实现-Unity

    .NET中实现IOC有很多方式,比如:Unity.Ninject.Autofac.MEFNinject的实现参考<Pro ASP.NET MVC3.5 FrameWork>下面给出的是Un ...

  6. 编译 SharpNav 遇到的问题和解决过程

    https://github.com/Robmaister/SharpNav 是github上基于recastnavtigation的一个C#项目. github上并没有详细的编译过程. 首先把项目c ...

  7. 如何使用Visual Studio Code调试PHP CLI应用和Web应用

    在按照Jerry的公众号文章 什么?在SAP中国研究院里还需要会PHP开发? 进行XDebug在本地的配置之后,如果想使用Visual Studio Code而不是Eclipse来调试PHP应用,步骤 ...

  8. 【大数据】SmallFile-Analysis-Script

    1.root账号先在namenode节点上配置一个定时任务,将fsimage定时传到其他客户机上进行操作 whereis hadoop命令确定安装目录,然后去配置文件找到namenode节点(data ...

  9. 彻底弄懂HTTP缓存机制及原理-转载

    首先附上原文地址,非常感谢博主大神的分享彻底弄懂HTTP缓存机制及原理 前言     Http 缓存机制作为 web 性能优化的重要手段,对于从事 Web 开发的同学们来说,应该是知识体系库中的一个基 ...

  10. 10 Windows编程——鼠标消息

    和鼠标相关的三个属于:click,double-click,drag 鼠标消息和键盘消息不同:只要鼠标跨越某个窗口,或者在某个窗口中按键,消息. 客户去鼠标消息 WM_MOUSEMOVE WM_[L, ...