[POJ1201]Intervals

题目大意:
  给数轴上一些整点做标记。
  告诉你n条信息,表示[a,b]中有c个做了标记,问至少有几个数被做了标记。

思路:
  给a-1到b连一条权值为c的边,给所有的i-1到i连一条权值为0的边,i到i-1连一条权值为-1的边,SPFA跑差分约束即可。

 1 #include<queue>
 2 #include<cstdio>
 3 #include<cctype>
 4 #include<vector>
 5 #include<cstring>
 6 inline int getint() {
 7     register char ch;
 8     while(!isdigit(ch=getchar()));
 9     register int x=ch^'0';
10     while(isdigit(ch=getchar())) x=(((x<<2)+x)<<1)+(ch^'0');
11     return x;
12 }
13 const int N=50001;
14 struct Edge {
15     int to,w;
16 };
17 std::vector<Edge> e[N];
18 inline void add_edge(const int &u,const int &v,const int &w) {
19     e[u].push_back((Edge){v,w});
20 }
21 std::queue<int> q;
22 bool inq[N];
23 int dis[N];
24 int main() {
25     const int n=getint();
26     int m=0;
27     for(register int i=0;i<n;i++) {
28         const int a=getint(),b=getint(),c=getint();
29         add_edge(a-1,b,c);
30         m=std::max(m,b);
31     }
32     for(register int i=1;i<=m;i++) {
33         add_edge(i-1,i,0);
34         add_edge(i,i-1,-1);
35     }
36     q.push(0);
37     inq[0]=true;
38     for(register int i=1;i<=m;i++) dis[i]=-1;
39     while(!q.empty()) {
40         const int x=q.front();
41         q.pop();
42         inq[x]=false;
43         for(unsigned i=0;i<e[x].size();i++) {
44             const int &y=e[x][i].to,&w=e[x][i].w;
45             if(dis[x]+w>dis[y]) {
46                 dis[y]=dis[x]+w;
47                 if(!inq[y]) {
48                     q.push(y);
49                     inq[y]=true;
50                 }
51             }
52         }
53     }
54     printf("%d\n",dis[m]);
55     return 0;
56 }

 

posted @ 2017-12-29 16:25  skylee03  阅读(103)  评论(0编辑  收藏  举报