[World Final 2016] Branch Assignment
链接
先求出正置边和反置边时b+1到前b个点的最短路dis[0/1][x](x∈[1,b]),
令D[x]=dis[0][x]+dis[1][x]
然后分组后每个x对代价的贡献为D[x]*(所在组中元素个数-1)
考虑DP决策分组过程,发现没有一个很好的序,
不过为了使得代价小,应该把D小的放在个数大的组里,D大的放在个数少的组里
由此可以想出,应该是大小相近的元素放在了同一组中,这意味着,先排序,在划分成s段,的所有情况包含了原问题的最优解
于是把D[1~b]排序后,有方程
$f[i][j]=MIN_{k=0}^{j-1}[f[i-1][k]+(j-k-1)*(sum[j]-sum[k])]$
$O(n^3)$
其中:f[i][j]表示把前j个分成i组的最小值,sum为D的前缀和
非法状态均置为INF
由于可以粗略的知道这个东西在j确定,i为自变量的函数图像上有凸性
(可以玄学地认为,最开始的时候,多划分一刀可以造成很大的改变,随着划分次数越来越多,多划分一刀的改变越来越微小)
于是,可以使用带权二分来优化这一DP
即,消去对划分次数的限制,通过二分来找到一个合适的划分附加代价,使得即使不限制划分次数,最后的最优解也恰好满足我们对划分数的限制
这样有了一个新的方程
$f'[j]=MIN_{k=0}^{j-1}[f'[k]+(j-k-1)*(sum[j]-sum[k])]+C$
$O(n^2log)$
考虑优化转移过程
拆开方程得到
$f'[j]=MIN_{k=0}^{j-1}[f'[k]+(k+1)sum[k]-ksum[j]-jsum[k]]+(j-1)sum[j]+C$
在方程中
当固定j不动时
随k增加,f'[k]+(k+1)sum[k]项增加,-ksum[j]-jsum[k]项减小
而随j的增加,含j的项(即-ksum[j]-jsum[k])对答案的影响加剧,于是,随j的增加,j的最优决策中的k会单调变大(随j的增加,我们决策时更为看重含j项,为了使含j项减小,我们试图使用更大的k)
这意味着这个方程有决策单调性
本题通过带权二分和决策单调性优化可以做到$O(nlog^2)$
(感觉最近状态很差,午休一直睡不着来着,几个月了吧,先是用N^2log给方哥号上贡献了半屏T,又以为可以nlog做,然后贡献了半屏Wa,最后才发现决策单调性)
代码:
#include<queue>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define LL long long
#define P pair <int ,int >
using namespace std;
priority_queue <P ,vector <P > ,greater <P > > PQ ;
int n,b,s,r;
struct INP{
int u,v,val;
}inp[];
struct ss{
int to,next,val;
}e[];
int first[],num;
LL d[],f[],sum[];
int lin[],dis[],que[],grt_st[];
void build(int ,int ,int );
void dij(int );
bool check(LL );
LL ask(int ,int );
int main()
{
int i,j,k,l;
LL L,R,mid;
scanf("%d%d%d%d",&n,&b,&s,&r);
for(i=;i<=r;i++){
scanf("%d%d%d",&inp[i].u,&inp[i].v,&inp[i].val);
build(inp[i].u,inp[i].v,inp[i].val);
}
dij(b+);
for(i=;i<=b;i++) d[i]=dis[i];
memset(first,,sizeof(first)),num=;
for(i=;i<=r;i++)
build(inp[i].v,inp[i].u,inp[i].val);
dij(b+);
for(i=;i<=b;i++) d[i]+=dis[i];
sort(d+,d+b+);
for(i=;i<=b;i++) sum[i]=sum[i-]+d[i];
L=,R=b*sum[b],mid=(L+R)>>;
while(R-L>=){
if(check(mid)) L=mid;
else R=mid-;
mid=(L+R)>>;
}
for(mid=R;mid>=L;mid--)
if(check(mid)){
printf("%lld\n",f[b]-s*mid);
return ;
}
return ;
}
void build(int f,int t,int val){
e[++num].next=first[f];
e[num].to=t,e[num].val=val;
first[f]=num;
}
void dij(int S){
int i,U;
memset(dis,0x3f,sizeof(dis));
dis[S]=;
P u,v;
u.first=,u.second=S;
PQ.push(u);
while(!PQ.empty()){
u=PQ.top();
PQ.pop();
U=u.second;
for(i=first[U];i;i=e[i].next)
if(dis[e[i].to]>dis[U]+e[i].val){
dis[e[i].to]=dis[U]+e[i].val;
v.first=dis[e[i].to],v.second=e[i].to;
PQ.push(v);
}
}
}
bool check(LL lim){
int tmp=,i,h=,t=;
int l,r,mid;
f[]=lin[]=,grt_st[]=;
que[t]=;
for(i=;i<=b;i++){
l=h+,r=t,mid=(l+r)>>;
while(r-l>){
if(i>=grt_st[que[mid]]) l=mid;
else r=mid-;
mid=(l+r)>>;
}
for(mid=r;mid>=l;mid--)
if(i>=grt_st[que[mid]]){
f[i]=ask(i,que[mid])+lim,lin[i]=lin[que[mid]]+;
break;
}
if(i==b) break;
grt_st[i]=b+;
while(h<t&&grt_st[que[t]]>i&&ask(grt_st[que[t]],i)<=ask(grt_st[que[t]],que[t])) grt_st[i]=grt_st[que[t]],t--;
if(h<t){
l=max(grt_st[que[t]],i+),r=grt_st[i]-,mid=(l+r)>>;
while(r-l>){
if(ask(mid,i)<=ask(mid,que[t])) r=mid;
else l=mid+;
mid=(l+r)>>;
}
for(mid=l;mid<=r;mid++)
if(ask(mid,i)<=ask(mid,que[t])){
grt_st[i]=mid;
break;
}
}
if(grt_st[i]!=b+)
que[++t]=i;
}
return lin[b]>=s;
}
LL ask(int x,int typ){
return f[typ]+(x-typ-)*(sum[x]-sum[typ]);
}
[World Final 2016] Branch Assignment的更多相关文章
- 4609: [Wf2016]Branch Assignment 最短路 DP (阅读理解题)
Bzoj的翻译出锅了所以来官方题面:这个题应该是单向边而BZOJ说的是双向边,什么你WA了?谁叫你懒得看英文...... 显然我们能正向反向两遍SPFA处理出每个点到总部的距离和总部到每个点的距离.如 ...
- Gym-101242B:Branch Assignment(最短路,四边形不等式优化DP)
题意:要完成一个由s个子项目组成的项目,给b(b>=s)个部门分配,从而把b个部门分成s个组.分组完成后,每一组的任 意两个点之间都要传递信息.假设在(i,j)两个点间传送信息,要先把信息加密, ...
- bzoj AC倒序
Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...
- BZOJ 4619 Swap Space 解题报告
今天是因为David Lee正好讲这个题的类似题,我才做了一下. 本题是world final 2016的一道水…… 题目地址如下 http://www.lydsy.com/JudgeOnline/p ...
- Kafka Consumer2
本文记录了和conumser相关的几个类. 首先是RequestFuture这个类,consumer和服务端通信使用它作为返回值. 其次是HeartBeat机制,consumer和coordinato ...
- JGit----将 Git 嵌入你的应用
如果你想在一个 Java 程序中使用 Git ,有一个功能齐全的 Git 库,那就是 JGit . JGit 是一个用 Java 写成的功能相对健全的 Git 的实现,它在 Java 社区中被广泛使用 ...
- 2016/09/21 Java关键字final
1.final类 final类不能被继承,没有子类,final类中的方法默认是final的. final类不能被继承,因此final类的成员方法没有机会被覆盖,默认都是final的. 2.final方 ...
- 2016 China Collegiate Programming Contest Final
2016 China Collegiate Programming Contest Final Table of Contents 2016 China Collegiate Programming ...
- Atcoder CODE FESTIVAL 2016 Grand Final E - Water Distribution
Atcoder CODE FESTIVAL 2016 Grand Final E - Water Distribution 题目链接:https://atcoder.jp/contests/cf16- ...
随机推荐
- mybatis四大接口之 ResultSetHandler
1. 继承结构 2. ResultSetHandler public interface ResultSetHandler { // 将Statement执行后产生的结果集(可能有多个结果集)映射为结 ...
- async await 的执行
async await的执行 注意:本次代码仅在 Chrome 73 下进行测试. start 不了解 async await 的,先去看阮一峰老师的文章async 函数. 先来看一道头条的面试题,这 ...
- canvars 画花
index.html <!DOCTYPE html><html><head> <title>旋转的花</title> <meta ch ...
- Consul使用
- 课程二(Improving Deep Neural Networks: Hyperparameter tuning, Regularization and Optimization),第三周(Hyperparameter tuning, Batch Normalization and Programming Frameworks) —— 2.Programming assignments
Tensorflow Welcome to the Tensorflow Tutorial! In this notebook you will learn all the basics of Ten ...
- 开机自启动Nginx的脚本
1.1 编写shell脚本 这里使用的是编写shell脚本的方式来处理 vi /etc/init.d/nginx (输入下面的代码) #!/bin/bash # nginx Startup scri ...
- Redis笔记(1)数据结构与对象
1.前言 此系列博客记录redis设计与实现一书的笔记,提取书本中的知识点,省略相关说明,方便查阅. 2.基本数据结构 2.1 简单动态字符串SDS(simple dynamic string) 结构 ...
- 【奔走相告】- Github送福利:用户可免费创建私有代码库啦
最新消息 PingWest品玩1月8日讯,据TheNextWeb消息,据美国科技媒体The Next Web报道,被微软收购的代码平台GitHub最近调整政策,用户免费创建无限空间私有代码库(priv ...
- INSERT INTO IF EXISTS
INSERT INTO books (name) SELECT 'MySQL Manual' FROM dual WHERE NOT EXISTS (SELECT id FROM booksWHERE ...
- 第一章 Java Web工作原理
一:在本章我们将学到如下的内容 >HTTP协议原理 >服务器端Web编程原理 >Servlet与Web容器 >Java Web应用程序的组成 >Tomcat介绍 一:1. ...