POJ 1201 Intervals (差分约束,最短路)
题意:
有一个集合Z,其元素都是整整数,但是数量未知。现有n个约束,形如 [a,b]=c 表示整数区间[a,b]中有c个元素在Z中出现。问集合Z最小可能含多少个元素?
思路:
对于所给的区间 cnt[b-a]>=k这可以保证了该区间内个数不少于k。但是由于两边都是闭区间,所以要变cnt[b-(a-1)]>=k,表示b到a之间的个数。也就是说,转成式子是b-(a-1)>=k,变换一下为(a-1)-b<=-k,就满足常见的式子b-a<=k啦,可以建边b指向(a-1),权值为-k。
但是还有没有其他的约束条件呢?如果我们只是这样建图,那很多个点都不会有联系的啊,比如[3,7]>=2和 [5,9]>=4,建边为2->7和4>9,完全不搭边啊!肯定还有其他联系,相邻的两个数字之间是否可以有边?可以的,至少可以满足a-(a-1)>=0吧?表示a只能被选与不被选。还有呢?每个点最多只能被选一次吧?则有a-(a-1)<=1。
综合3条式子,可以变形得到:
(1)(a-1)-b<=-k
(2)(a-1)-a<=0
(3)a-(a-1)<=1
都满足了常见的式子。那么可以建边了。这下每两个相邻数字就起码有两条边。注意:求的值是最小的,所以标准形式用<=号。
我们要求的是什么?满足要求的,整个区间所挑的最小个数。从最大数字出发,进行求最短路后,最小的数的那个点通常就会得到一个负权路径和啦,cost[最小]=负值。而cost[最小]取相反数就是答案了。记得开始前要将cost[起点]置为0。大概思路是这样,但是区间是[0,50000],所以0-1时还会出现负数下标,可以将整个区间右移一位变成[1,50001]。
//#include <bits/stdc++.h>
#include <cstdio>
#include <cstring>
#include <map>
#include <iostream>
#include <deque>
#include <vector>
#define INF 0x7f7f7f7f
#define pii pair<int,int>
#define LL unsigned long long
using namespace std;
const int N=;
struct node
{
int from,to,cost;
node(){};
node(int from,int to,int cost):from(from),to(to),cost(cost){};
}edge[N*];
vector<int> vect[N];
int edge_cnt; void add_node(int from,int to,int cost)
{
edge[edge_cnt]=node(from,to,cost);
vect[from].push_back(edge_cnt++);
} bool inq[N];
int cost[N];
int spfa(int small,int big)
{
memset(inq, , sizeof(inq));
memset(cost, 0x7f, sizeof(cost));
cost[big]=;
deque<int> que(,big); while(!que.empty())
{
int x=que.front();que.pop_front();
inq[x]=; for(int i=; i<vect[x].size(); i++)
{
node e=edge[vect[x][i]];
if(cost[e.to]>cost[x]+e.cost)
{
cost[e.to]=cost[x]+e.cost;
if(!inq[e.to])
{
inq[e.to]=;
if(!que.empty() && cost[e.to]<cost[que.front()]) que.push_front(e.to);
else que.push_back(e.to);
}
}
}
}
return -cost[small];
} int main()
{
//freopen("input.txt", "r", stdin);
int n, m, a, b, c;
while(~scanf("%d",&n))
{
edge_cnt=;
memset(edge,,sizeof(edge));
for(int i=; i<N; i++) vect[i].clear();
int small=INF, big=; for(int i=; i<n; i++)
{
scanf("%d%d%d",&a,&b,&c);
add_node(b+,a,-c); //右移了1位 small=min(small, a+);
big=max(big, b+);
}
//每两个点之间的
for(int i=small; i<=big; i++)
{
add_node(i-, i, );
add_node(i, i-, );
}
cout<<spfa(small-, big)<<endl;
}
return ;
}
AC代码
POJ 1201 Intervals (差分约束,最短路)的更多相关文章
- poj 1201 Intervals(差分约束)
题目:http://poj.org/problem?id=1201 题意:给定n组数据,每组有ai,bi,ci,要求在区间[ai,bi]内至少找ci个数, 并使得找的数字组成的数组Z的长度最小. #i ...
- poj 1201 Intervals——差分约束裸题
题目:http://poj.org/problem?id=1201 差分约束裸套路:前缀和 本题可以不把源点向每个点连一条0的边,可以直接把0点作为源点.这样会快许多! 可能是因为 i-1 向 i 都 ...
- POJ 1201 Intervals (差分约束系统)
题意 在区间[0,50000]上有一些整点,并且满足n个约束条件:在区间[ui, vi]上至少有ci个整点,问区间[0, 50000]上至少要有几个整点. 思路 差分约束求最小值.把不等式都转换为&g ...
- POJ 2101 Intervals 差分约束
Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 27746 Accepted: 10687 Description You ...
- poj 1201 Intervals(差分约束)
做的第一道差分约束的题目,思考了一天,终于把差分约束弄懂了O(∩_∩)O哈哈~ 题意(略坑):三元组{ai,bi,ci},表示区间[ai,bi]上至少要有ci个数字相同,其实就是说,在区间[0,500 ...
- POJ 1201 Intervals【差分约束】
传送门:http://poj.org/problem?id=1201 题意: 有n个如下形式的条件:,表示在区间[, ]内至少要选择个整数点.问你满足以上所有条件,最少需要选多少个点? 思路:第一道差 ...
- POJ 1201 Intervals (经典) (差分约束)
<题目链接> 题目大意:给你$n$段区间,$a_i,b_i,c_i$ 表示在 $[a_i,b_i]$ 区间内至少要选择$c_i$个点.现在问你在满足这n个条件的情况下,最少要选多少个点? ...
- poj 1201 Intervals【差分约束+spfa】
设s为前缀和,首先显然的条件是\[ s_{bi}-s_{ai-1}>=c \],然后隐含的是\[ s_i-s_{i-1}>=0 s_i-s_{i-1}<=1 \] 然后根据差分约束, ...
- 【题解】 POJ 1201 Intervals(差分约束)
懒得复制,戳我戳我 Solution: 这道题就是一个板子题 抽象成第\(a\)至第\(b\)间选择数的个数为\(c\),我们就可以用前缀和来表示,这样就可以得到不等式\(s[b]-s[a-1]> ...
- POJ 1201 Intervals(差分约束 区间约束模版)
关于差分约束详情可阅读:http://www.cppblog.com/menjitianya/archive/2015/11/19/212292.html 题意: 给定n个区间[L,R], 每个区间至 ...
随机推荐
- HDU 4597 Play Game(记忆化搜索,深搜)
题目 //传说中的记忆化搜索,好吧,就是用深搜//多做题吧,,这个解法是搜来的,蛮好理解的 //题目大意:给出两堆牌,只能从最上和最下取,然后两个人轮流取,都按照自己最优的策略,//问说第一个人对多的 ...
- ios网站,博客
中文 网站系列 objcio.cncocoachina.comcode4app.com泰然网 博客系列唐巧地球人都知道哈.http://blog.devtang.com/巧哥新出书了,速度入手吧. 虾 ...
- 有趣 GIF 动图集 - 仿佛每张小动图都诉说了一个小笑话或者小故事
点这里 来自法国南特(Nantes)的 Guillaume Kurkdjian 目前还是个学生.Kurkdjian 擅长创作一些平面动态图像,这些有趣的小动图仿佛每张都诉说了一个小笑话或者小故事,像个 ...
- HDU 1789 Doing Homework again (贪心)
Doing Homework again http://acm.hdu.edu.cn/showproblem.php?pid=1789 Problem Description Ignatius has ...
- java集合TreeMap应用---求一个字符串中,每一个字母出现的次数
package cn.itcast.p1.map.test; import java.util.Iterator; import java.util.Map; import java.util.Tre ...
- hdu 3886 Final Kichiku “Lanlanshu” 数位DP
思路: dp[i][j][k]:满足在字符串的j位,前一位数字是k. 代码如下: #include<iostream> #include<cstdio> #include< ...
- java.lang.ClassCastException: sun.jdbc.odbc.JdbcOdbcStatement cannot be cast to java.beans.Statement
当导入的包为:import java.sql.Statement;时,无任何错误 当导入的包为:import java.beans.Statement;时,出错
- win8,定时任务添加(schtasks)
win8,64位,通过CMD命令schtasks,添加定时任务 以下内容,均来自 schtasks /? 和 schtasks /create /? // 1.schtasks /create 的参数 ...
- 【转】java线程系列---Runnable和Thread的区别
在java中可有两种方式实现多线程,一种是继承Thread类,一种是实现Runnable接口:Thread类是在java.lang包中定义的.一个类只要继承了Thread类同时覆写了本类中的run() ...
- Ffmpeg解析media容器过程/ ffmpeg 源代码简单分析 : av_read_frame()
ffmpeg 源代码简单分析 : av_read_frame() http://blog.csdn.net/leixiaohua1020/article/details/12678577 ffmpeg ...