http://poj.org/problem?id=1201

看了 两天差分约束题今天总算有点明白了,,做差分约束题,,就是通过合理的建立数学模型,将不等式图形化,,用bellmanford做武器,最终AC该题,,,。

这一题让求的是在区间a-b上至少可以取多少点,,,因此可以》=建图求图中的最长路径就ok了,但是有一点难点是建图的时候,并不是以两个端点建的图,而是以a,b+1来建的图,,因为如果这样的可能会出现错误,,比如<1,3>2,<3,6>2,因此可得<1,6>最少可以取4个点而这和实际情况相反,,,实际在该区间内最少可取3个,因此要换一种方式建图,,就是以a,b的左闭又开区间见图,,而在取点时候不会导致多取和少取,,,还有一点为了保证图的连通性,每个相邻的两个点至少可取0

个至多可取1个因此这个要特别考虑一下,,









求最长路径:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<string.h>
#include<stack>
#define N    50005
#define M  999999999
using namespace std;
int n,m,s,size;
struct Node{ int to,len,next;
       }node[N*3];
bool visit[N];
int adj[N];
int dist[N];
void init()
{   size=0;
    m=M,s=-1;
    memset(visit,false,sizeof(visit));
    for(int i=1;i<=N;i++)
    adj[i]=-1;
}
void Add(int a,int b,int c)
{   node[size].to=b;
    node[size].len=c;
    node[size].next=adj[a];
    adj[a]=size++; 
 }
 void spfa()
 {    for(int i=m;i<=s;++i)
        dist[i]=-M;
      stack<int> Q;
   dist[m]=0,visit[m]=true;
    Q.push(m);
     while(!Q.empty())
     {   int u=Q.top();
         Q.pop();
         visit[u]=false;
         for(int i=adj[u];i!=-1;i=node[i].next)
           {  int v=node[i].to;
               int l=node[i].len;
                if(dist[v]<dist[u]+l)
                  {  dist[v]=dist[u]+l;
                      if(!visit[v])
                      {  Q.push(v);
                         visit[v]=true;
                       }
                  }
                }
           }
           printf("%d\n",dist[s]);
      }
 int main()
 {   scanf("%d",&n);
      init();
         int a,b,c;
        for(int i=1;i<=n;++i)
         {   scanf("%d%d%d",&a,&b,&c);
              Add(a,b+1,c);
              if(m>a) m=a;
              if(s<b+1) s=b+1;
         }
         for(int i=m;i<=s;++i)//保证图的连通性,
          {      Add(i,i+1,0);
                 Add(i+1,i,-1);
          }
         spfa();
         //system("pause");
     }
  

求最短路径:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<string.h>
#include<stack>
#define N    50005
#define M  999999999
using namespace std;
int n,m,s,size;
struct Node{ int to,len,next;
       }node[N*3];
bool visit[N];
int adj[N];
int dist[N];
void init()
{   size=0;
    m=M,s=-1;
    memset(visit,false,sizeof(visit));
    for(int i=1;i<=N;i++)
    adj[i]=-1;
}
void Add(int a,int b,int c)
{   node[size].to=b;
    node[size].len=c;
    node[size].next=adj[a];
    adj[a]=size++; 
 }
 void spfa()
 {    for(int i=m;i<=s;++i)
        dist[i]=M;
      stack<int> Q;
   dist[m]=0,visit[m]=true;
    Q.push(m);
     while(!Q.empty())
     {   int u=Q.top();
         Q.pop();
         visit[u]=false;
         for(int i=adj[u];i!=-1;i=node[i].next)
           {  int v=node[i].to;
               int l=node[i].len;
                if(dist[v]>dist[u]+l)
                  {  dist[v]=dist[u]+l;
                      if(!visit[v])
                      {  Q.push(v);
                         visit[v]=true;
                       }
                  }
                }
           }
           printf("%d\n",-dist[s]);
      }
 int main()
 {   scanf("%d",&n);
      init();
         int a,b,c;
        for(int i=1;i<=n;++i)
         {   scanf("%d%d%d",&a,&b,&c);
              Add(a,b+1,-c);
              if(m>a) m=a;
              if(s<b+1) s=b+1;
         }
         for(int i=m;i<=s;++i)//保证图的连通性,
          {      Add(i+1,i,1);
                 Add(i,i+1,0);
          }
         spfa();
         //system("pause");
     }
 



你可能感兴趣的:(http://poj.org/problem?id=1201)