POJ 1201 Intervals[差分约束]

#include<stdio.h>

#include<string.h>

#include<iostream>

using namespace std;

#define N 1000005

#define INF 999999999

int head[N], vis[N], queue[N], dis[N], outqueue[N];

int n, index;



struct Edge

{

    int v, value, next;

}edge[N];

void add_Edge(int u, int v, int val)

{

    edge[index].next=head[u];

    edge[index].v=v;

    edge[index].value=val;

    head[u]=index++;

}



void Spfa(int s)

{

    int iq=0, front=0, i, top;

    memset(vis, 0, sizeof(vis));

    memset(outqueue, 0, sizeof(outqueue));

    for(i=1; i<=n; i++)

        dis[i]=INF;

    dis[s]=0;

    queue[iq++]=s;

    vis[s]=1;

    while(iq!=front)

    {

        top=queue[front];

        front++;

        vis[top]=0;

        outqueue[top]++;

        if(outqueue[top]>n)  return ;

        for(i=head[top]; i!=-1; i=edge[i].next)

        {

            if(dis[top]+edge[i].value<dis[edge[i].v])

            {

                dis[edge[i].v]=dis[top]+edge[i].value;

                if(vis[edge[i].v]==0)

                {

                    vis[edge[i].v]=1;

                    queue[iq++]=edge[i].v;

                }

            }

        }

    }

}

int main()

{

    int nn, a, b, c, i, maxn;

    while(scanf("%d", &n)!=EOF)

    {

        maxn=0, index=0;

        memset(head, -1, sizeof(head));

        for(i=0; i<n; i++)

        {

            scanf("%d%d%d", &a, &b, &c);

            maxn=max(maxn, b);

            add_Edge(a-1, b, -1*c);

        }

        for(i=1; i<=maxn; i++)

        {

            add_Edge(i, i-1, 1);

            add_Edge(i-1, i, 0);

        }

        n=maxn;

        Spfa(0);

        printf("%d\n", -1*dis[maxn]);

    }

    return 0;

}
View Code

 

题目链接:http://poj.org/problem?id=1201

题目大意:有一个集合,给出n个关系,每组关系三个数a, b, c代表[a, b]区间最少c个数。求出集合中做少有多少个数字

解题思路:[差分约束] 1.我们首先要转化成差分约束的特征形势x-y<=z的形势。

2.我们设ti表示i之前的区间有多少个数。那么tb-t(a-1)>=c ---(变形)--->t(a-1)-tb<=-c;

由于ti我们有合理的意义,那么0=<ti-t(i-1)<=1,即相邻两个数区间最多增加1个数 变形得到:ti-t(i-1)<=1  t(i-1)-ti<=0

3.组合上面的条件,得到差分约束系统。建图

4.用spfa算法求解最短路

5.由于t(a-1)-tb<=-c,c加了负号, 因此得出的结果要从负数变为整数

 代码如下:

 

你可能感兴趣的:(差分约束)