传送门 >Here<

题意:给出N段区间,并告诉你每段区间里有几个数(一个位置只能放一个数) 问总共至少有几个数

解题思路

  差分约束题,本蒟蒻也是第一次做差分约束题……

  所谓差分约束,常常是通过最短路(或最长路)来解决一些约束问题,例如不等式组

  举个例子:$$x1 -x2 \leq a1 (1)$$$$x2 -x3 \leq a2 (2)$$$$x1 -x3 \leq a3 (3)$$求解$x1-x3$的解集

  则我们可以让1~2连一条长度为a1的有向边,2~3连一条长度为a2的有向边,1~3连一条长度为a3的有向边

  我们会发现$(1)+(2)$可以得到$x1 - x3 \leq a1 + a2$(利用了不等式之间相加的定理),因此得到一组不等式组$$x1 - x3 \leq a1 + a2$$$$x1 -x3 \leq a3 (3)$$

  而最终由于是小于等于的约数,解集应当取$Min\{ a1+a2, a3 \}$

  为什么可以转化为最短路问题呢?考虑一条路径,对于所有非起点且非终点的点,与其相邻的路径上的两个点对应了两条路径,不妨设为$a-s,s-b$,则当这两个不等式相加时,中介点$s$一定会被消掉。宏观来看,一条路径上所有非起点终点的点都将为被抵消掉。因此最后只剩下路径的头尾了。而要求解集,如果是$<$,则应该取最小值,也就是最短路了。

  以上是差分约束的基本概念。那么回到这道题来,好像和差分约束没什么关系?

  光看好像是没什么关系。由于是考虑区间内数的个数,不妨设想有一个前缀和数组s,这样$[a_i, b_i]$至少有$c_i$个元素就可以表示成$s[b_i] - s[a_i-1] >= c[i]$,我们会得到若干个这样的不等式,就可以做差分约束了——然而值得注意的是,刚才的例子里是小于等于,而这里是大于等于。所以这里的解集应当取到最大,所以求的是最长路而不是最短路

  真的仅仅只是这样吗?我们忽略了题目给的一个条件——每个位置只能放一个数,所以我们的约束条件少了,要加上对于每一个位置i,$s[i]-s[i-1] \geq 0, s[i]-s[i-1] \leq 1$(其实$s[i]-s[i-1]$)就是i这个位置的数的个数,不是0就是1. 对于小于等于的情况,同时乘以-1转换成大于等于的形式,$s[i-1]-s[i] \geq -1$即可

code

  注意Dijkstra是不能做负权的(有$s[i-1]-s[i] \geq -1$的存在),所以用SPFA

/*By QiXingzhi*/
#include <cstdio>
#include <cstring>
#include <queue>
#include <algorithm>
#define r read()
#define Max(a,b) (((a)>(b)) ? (a) : (b))
#define Min(a,b) (((a)<(b)) ? (a) : (b))
using namespace std;
typedef long long ll;
const int MAXN = ;
const int INF = ;
inline int read(){
int x = ; int w = ; register int c = getchar();
while(c ^ '-' && (c < '' || c > '')) c = getchar();
if(c == '-') w = -, c = getchar();
while(c >= '' && c <= '') x = (x << ) +(x << ) + c - '', c = getchar();
return x * w;
}
int N,L,R;
int a,b,c,d[MAXN],vis[MAXN];
int first[MAXN*],nxt[MAXN*],to[MAXN*],cost[MAXN*],num_edge;
queue <int> q;
inline void add(int u, int v, int w){
// printf("%d->%d (%d)\n", u,v,w);
to[++num_edge] = v;
cost[num_edge] = w;
nxt[num_edge] = first[u];
first[u] = num_edge;
}
inline void SPFA(int s){
for(int i = ; i <= N; ++i) d[i] = -INF;
d[s] = ;
q.push(s);
int u, v;
while(!q.empty()){
u = q.front();
q.pop();
vis[u] = ;
for(int i = first[u]; i; i = nxt[i]){
v = to[i];
if(d[u] + cost[i] > d[v]){
d[v] = d[u] + cost[i];
if(!vis[v]){
vis[v] = ;
q.push(v);
}
}
}
}
}
inline void Init(){
memset(vis,,sizeof(vis));
memset(first,,sizeof(first));
memset(nxt,,sizeof(nxt));
memset(to,,sizeof(to));
memset(cost,,sizeof(cost));
}
int main(){
// freopen(".in","r",stdin);
while(scanf("%d",&N) == ){
L = N+, R = -;
Init();
for(int i = ; i <= N; ++i){
a=r,b=r,c=r;
add(a, b+, c);
L = Min(L, a);
R = Max(R, b+);
}
for(int i = ; i <= R; ++i){
add(i+, i, -);
add(i, i+, );
}
SPFA(L);
// printf("R+1 = %d L+1 = %d\n",R+1,L+1);
printf("%d\n", d[R]);
}
return ;
}

☆ [POJ1021] Intervals 「差分约束」的更多相关文章

  1. poj1716 Integer Intervals(差分约束)

    转载请注明出处: http://www.cnblogs.com/fraud/          ——by fraud Integer Intervals Time Limit: 1000MS   Me ...

  2. POJ1201 Intervals (差分约束)

    You are given n closed, integer intervals [ai, bi] and n integers c1, ..., cn. Write a program that: ...

  3. poj 1716 Integer Intervals(差分约束)

    1716 -- Integer Intervals 跟之前个人赛的一道二分加差分约束差不多,也是求满足条件的最小值. 题意是,给出若干区间,需要找出最少的元素个数,使得每个区间至少包含两个这里的元素. ...

  4. poj 1201 Intervals(差分约束)

    做的第一道差分约束的题目,思考了一天,终于把差分约束弄懂了O(∩_∩)O哈哈~ 题意(略坑):三元组{ai,bi,ci},表示区间[ai,bi]上至少要有ci个数字相同,其实就是说,在区间[0,500 ...

  5. Intervals(差分约束)

    http://poj.org/problem?id=1201 题意:给出N个整数区间[ai,bi],并且给出一个约束ci,( 1<= ci <= bi-ai+1),使得数组Z在区间[ai, ...

  6. POJ 1201 Intervals (经典) (差分约束)

    <题目链接> 题目大意:给你$n$段区间,$a_i,b_i,c_i$ 表示在 $[a_i,b_i]$ 区间内至少要选择$c_i$个点.现在问你在满足这n个条件的情况下,最少要选多少个点? ...

  7. HDU 1384 Intervals【差分约束-SPFA】

    类型:给出一些形如a−b<=k的不等式(或a−b>=k或a−b<k或a−b>k等),问是否有解[是否有负环]或求差的极值[最短/长路径].例子:b−a<=k1,c−b&l ...

  8. 【题解】 POJ 1201 Intervals(差分约束)

    懒得复制,戳我戳我 Solution: 这道题就是一个板子题 抽象成第\(a\)至第\(b\)间选择数的个数为\(c\),我们就可以用前缀和来表示,这样就可以得到不等式\(s[b]-s[a-1]> ...

  9. POJ1201 Intervals 【差分约束】

    题目链接 POJ1201 题解 差分约束 令\(a[i]\)表示是否选择\(i\),\(s[i]\)表示\(a[i]\)的前缀和 对\(s[i] \quad i \in [-1,50000]\)分别建 ...

随机推荐

  1. 内网IP外网IP的关联及访问互联网原理

    首先解释一下“内网”与“外网”的概念: 内网:即所说的局域网,比如学校的局域网,局域网内每台计算机的IP地址在本局域网内具有互异性,是不可重复的.但两个局域网内的内网IP可以有相同的. 外网:即互联网 ...

  2. 基于node.js的博客搭建

    一个博客应当具备哪些功能? 前台展示 点击下一页,可以点击分类导航. 可以点击进入到具体博文页面 下方允许评论.显示发表时间.允许留言分页. 右侧有登录注册界面. 后台管理 管理员账号:登陆后看到页面 ...

  3. Linux之磁盘挂载

    1.查看磁盘分区情况: fdisk -l 可以看到,红框中的硬盘没有分区. 2.开始分区: fdisk /dev/vdb 3.格式化分区: mkfs.xfs 分区名 4.挂载磁盘 挂载方式1: 手动挂 ...

  4. 文件传输协议FTP、SFTP和SCP

    网络通信协议分层 应用层: HTTP(Hypertext Transfer Protocol 超文本传输协议,显示网页) DNS(Domain Name System) FTP(File Transf ...

  5. java设计模式:面向对象设计的7个原则

    在软件开发中,为了提高软件系统的可维护性和可复用性,增加软件的可扩展性和灵活性,程序员要尽量根据7条原则来开发程序,从而提高软件开发效率,节约软件开发成本和维护成本. 这7条原则分别是:开闭原则.里氏 ...

  6. 记一次阿里云服务器被用作DDOS攻击肉鸡

    事件描述:阿里云报警 ——检测该异常事件意味着您服务器上开启了"Chargen/DNS/NTP/SNMP/SSDP"这些UDP端口服务,黑客通过向该ECS发送伪造源IP和源端口的恶 ...

  7. 使用mysqlbinlog恢复数据

    前提:mysql数据库开启了binlog日志,并且有对应的日志文件 起因:今天由于同事对数据库的误操作不小心删除了一条数据 方法一:通过binlog日志文件恢复数据 通过mysqlbinlog恢复My ...

  8. mybatis逆向工程,实现join多表查询,避免多表相同字段名的陷阱

    ​ mybatis逆向工程,实现join多表查询,避免多表相同字段名的陷阱 ​ 前言:使用 mybatis generator 生成表格对应的pojo.dao.mapper,以及对应的example的 ...

  9. linux 安装python 和pip

    下载文件 python官网:https://www.python.org/downloads/ 百度网盘http://pan.baidu.com/s/1mixGB12     密码   9nzu [r ...

  10. LODOP打印css样式rgba显示黑色区块

    当LODOP打印html超文本出现问题的时候,要删减排查一下样式,查看Lodop传入的内部的html超文本和样式,可查看本博客另一篇博文:删减发现有问题的样式,并解决该问题,尽量使用通用的css样式, ...