题意:有n个空心物品,每个物品有外部体积outi和内部体积ini,如果ini>outj,那么j就可以套在i里面。现在我们要选出n个物品的一个子集,这个子集内的k个物品全部套在一起,且剩下的物品都无法添加到这个子集中(没有空间塞进去)。

定义浪费的空间为子集中空心的部分,即ini1+(ini2−outi1)+(ini3−outi2)+⋯+(inik−outik−1)ini1+(ini2−outi1)+(ini3−outi2)+⋯+(inik−outik−1)。求浪费空间最少的子集个数。

解法:第一时间能想到最短路计数,但是朴素建图办法是n^2的。不会线段树优化建图,这里学习的是https://www.cnblogs.com/birchtree/p/11274812.html这位大佬的。

上面大佬的博客说得十分好了。线段树优化的原理其实就是通过一棵线段树当作工具树,这棵树不附带信息,只是作为一个桥梁连原图结点,且因为线段树能极短地表示区间的优点使得:向区间连边时极大的优化边数。

从而达到优化边数的目的。

upd:好像被新数据hack了

#include<bits/stdc++.h>
using namespace std;
const int N=1e6+;
const int MOD=1e9+;
int n,s,t,tot,p[N],b[N],tag[N],indeg[N],outdeg[N];
typedef long long LL;
struct dat{
int l,r;
bool operator < (const dat &rhs) const {
return r<rhs.r;
}
}a[N]; int cnt=,head[N],nxt[N<<],to[N<<],len[N<<];
void add_edge(int x,int y,int z) {
nxt[++cnt]=head[x]; to[cnt]=y; len[cnt]=z; head[x]=cnt;
indeg[y]++; outdeg[x]++;
} void build(int rt,int l,int r) {
tot=max(tot,rt);
if (l==r) {
p[l]=rt;
return;
}
int mid=l+r>>;
add_edge(rt,rt<<,); add_edge(rt,rt<<|,);
build(rt<<,l,mid);
build(rt<<|,mid+,r);
} void query(int rt,int l,int r,int ql,int qr,int i) {
if (ql<=l && r<=qr) {
add_edge(tot+i,rt,a[i].l);
return;
}
int mid=l+r>>;
if (ql<=mid) query(rt<<,l,mid,ql,qr,i);
if (qr>mid) query(rt<<|,mid+,r,ql,qr,i);
} queue<int> q;
LL dis[N],ans[N];
LL toposort() {
memset(dis,0x3f,sizeof(dis));
memset(ans,,sizeof(ans));
for (int i=;i<=n;i++) {
tag[i]+=tag[i-];
if (tag[i]==) add_edge(s,tot+i,);
else add_edge(p[i],tot+i,-a[i].r);
}
q.push(s); dis[s]=; ans[s]=;
add_edge(s,,0x3f3f3f3f);
while (!q.empty()) {
int x=q.front(); q.pop();
for (int i=head[x];i;i=nxt[i]) {
int y=to[i];
if (dis[x]+len[i]<dis[y]) {
dis[y]=dis[x]+len[i];
ans[y]=ans[x];
} else if (dis[x]+len[i]==dis[y]) {
ans[y]=(ans[x]+ans[y])%MOD;
}
if (--indeg[y]==) q.push(y);
}
}
return ans[t];
} int main()
{
scanf("%d",&n);
for (int i=;i<=n;i++) scanf("%d%d",&a[i].r,&a[i].l);
sort(a+,a+n+);
tot=;
build(,,n);
//for (int i=1;i<=n;i++) add_edge(p[i],tot+i,-a[i].r);
for (int i=;i<=n;i++) b[i]=a[i].r;
s=; t=tot+n+;
for (int i=;i<=n;i++) {
int tmp=upper_bound(b+,b+i+,a[i].l)-b-;
if (tmp>=) query(,,n,,tmp,i),tag[]++,tag[tmp+]--;
else add_edge(tot+i,t,);
} cout<<toposort()<<endl;
return ;
}

Educational Codeforces Round 69 E - Culture Code (最短路计数+线段树优化建图)的更多相关文章

  1. [Codeforces 1197E]Culture Code(线段树优化建图+DAG上最短路)

    [Codeforces 1197E]Culture Code(线段树优化建图+DAG上最短路) 题面 有n个空心物品,每个物品有外部体积\(out_i\)和内部体积\(in_i\),如果\(in_i& ...

  2. B - Legacy CodeForces - 787D 线段树优化建图+dij最短路 基本套路

    B - Legacy CodeForces - 787D 这个题目开始看过去还是很简单的,就是一个最短路,但是这个最短路的建图没有那么简单,因为直接的普通建图边太多了,肯定会超时的,所以要用线段树来优 ...

  3. 区间->点,点->区间,线段树优化建图+dijstra Codeforces Round #406 (Div. 2) D

    http://codeforces.com/contest/787/problem/D 题目大意:有n个点,三种有向边,这三种有向边一共加在一起有m个,然后起点是s,问,从s到所有点的最短路是多少? ...

  4. CodeForces 786B Legacy(线段树优化建图+最短路)

    [题目链接] http://codeforces.com/problemset/problem/786/B [题目大意] 给出一些星球,现在有一些传送枪,可以从一个星球到另一个星球, 从一个星球到另一 ...

  5. Educational Codeforces Round 81 (Rated for Div. 2)E(线段树)

    预处理把左集划分为大小为1~i-1时,把全部元素都移动到右集的代价,记作sum[i]. 然后枚举终态时左集的大小,更新把元素i 留在/移动到 左集的代价. 树状数组/线段树处理区间修改/区间查询 #d ...

  6. Educational Codeforces Round 73 (Rated for Div. 2)F(线段树,扫描线)

    这道题里线段树用来区间更新(每次给更大的区间加上当前区间的权重),用log的复杂度加快了更新速度,也用了区间查询(查询当前区间向右直至最右中以当前区间端点向右一段区间的和中最大的那一段的和),也用lo ...

  7. Educational Codeforces Round 72 (Rated for Div. 2)E(线段树,思维)

    #define HAVE_STRUCT_TIMESPEC#include<bits/stdc++.h>using namespace std;#define BUF_SIZE 100000 ...

  8. Codeforces.1045A.Last chance(最大流ISAP 线段树优化建图)

    题目链接 \(Description\) 你需要用给定的\(n\)个武器摧毁\(m\)架飞船中的某一些.每架飞船需要被摧毁恰好一次. 武器共三种:1.可以在给定的集合中摧毁一架飞船:2.可以摧毁区间\ ...

  9. Codeforces.786B.Legacy(线段树优化建图 最短路Dijkstra)

    题目链接 \(Description\) 有\(n\)个点.你有\(Q\)种项目可以选择(边都是有向边,每次给定\(t,u,v/lr,w\)): t==1,建一条\(u\to v\)的边,花费\(w\ ...

随机推荐

  1. maven多模块

    https://www.cnblogs.com/lichking2017/p/8996939.html

  2. springboot使用异步查询数据

    主要适用于需要查询多种类型的数据,而且二者的参数没有关联的情况. 1.开启异步调用注解 2.创建抽象类,定义相关方法 /** * @author:YZH * time: 2019/8/8 12:16 ...

  3. 返回结果的 HTTP 状态 码

    2xx 200:表示从客户端发来的请求在服务器端被正常处理了.   204:该状态码代表服务器接收的请求已成功处理,但在返回的响应报文中 不含实体的主体部分.另外,也不允许返回任何实体的主体.   2 ...

  4. Flutter的DateTime轉換的各種方法

    概述: 表示一个时间点 通过构造函数或解析格式化的字符串创建DateTime对象,并且符合ISO 8601标准的子集,小时是24小时制,范围在0-23之间 DateTime对象创建之后,将是固定不变的 ...

  5. 4,JPA

    一,什么是JPA JPA全称Java Persistence API.JPA通过JDK 5.0注解或XML描述对象-关系表的映射关系,并将运行期的实体对象持久化到数据库中. JPA(Java Pers ...

  6. 在VMware中配置网卡之NAT模式

    为什么要在VMware中配置网卡? 因为在远程连接服务器时,需要虚拟机连接网络 虚拟机网络配置的三种模式:桥接模式,NAT模式,主机模式 NAT模式也称之为网络转换模式,两层路由: 第一层路由:物理机 ...

  7. 09-排序3 Insertion or Heap Sort(25 分)

    According to Wikipedia: Insertion sort iterates, consuming one input element each repetition, and gr ...

  8. 【2019 Multi-University Training Contest 3】

    01: 02:https://www.cnblogs.com/myx12345/p/11593829.html 03: 04:https://www.cnblogs.com/myx12345/p/11 ...

  9. 【SpringBoot】 理解Spirng中的IOC原理

    前言 前文已经介绍了Spring Bean的生命周期,在这个周期内有一个重要的概念就是: IOC容器 大家也知道IOC是Sping 的重要核心之一,那么如何理解它呢,它又是产生什么作用呢?本文就IOC ...

  10. vue搭建项目之设置axios

    首先要下载axios: npm install axios -S 要注意的是,axios不支持Vue.use();这种方式,可以改写原型链. 第二步就是新建axios存放位置: 在项目中src中单独建 ...