Task Schedule HDU - 3572(按时间点建边)

问题描述
我们的几何公主XMM已经开始研究计算几何学,专注于她新开的工厂。她的工厂引进了M台新机器来处理即将到来的N个任务。对于第i个任务,工厂必须在第Si天或之后开始处理它,处理Pi天,并在Ei之前或之日完成任务。一台机器一次只能处理一个任务,每个任务最多可以由一台机器一次处理。但是,可以在不同的日期在不同的计算机上中断和处理任务。
现在,她想知道他是否有可行的时间表来及时完成所有任务。她求助于你。
解析:
  蒟蒻的我看成了无源汇上下界可行流。。。。
  好的吧  就是一个最大流 建立s和t    一共就500天  把每一天看作一个点 向t连边 容量为M   s向每个任务连边容量为Pi
  然后每个任务向它可以完成任务的时间范围内的点建边  容量为1 表示在那一天用1个机器
 
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<queue>
#include<vector>
#define INF 1e9
using namespace std;
const int maxn =+; struct Edge
{
int from,to,cap,flow;
Edge(){}
Edge(int f,int t,int c,int fl):from(f),to(t),cap(c),flow(fl){}
}; struct Dinic
{
int n,m,s,t;
vector<Edge> edges;
vector<int> G[maxn];
bool vis[maxn];
int cur[maxn];
int d[maxn]; void init(int n,int s,int t)
{
this->n=n, this->s=s, this->t=t;
edges.clear();
for(int i=;i<n;++i) G[i].clear();
} void AddEdge(int from,int to,int cap)
{
edges.push_back( Edge(from,to,cap,) );
edges.push_back( Edge(to,from,,) );
m=edges.size();
G[from].push_back(m-);
G[to].push_back(m-);
} bool BFS()
{
queue<int> Q;
memset(vis,,sizeof(vis));
vis[s]=true;
d[s]=;
Q.push(s);
while(!Q.empty())
{
int x=Q.front(); Q.pop();
for(int i=;i<G[x].size();++i)
{
Edge& e=edges[G[x][i]];
if(!vis[e.to] && e.cap>e.flow)
{
vis[e.to]=true;
d[e.to]=d[x]+;
Q.push(e.to);
}
}
}
return vis[t];
} int DFS(int x,int a)
{
if(x==t || a==) return a;
int flow=, f;
for(int &i=cur[x];i<G[x].size();++i)
{
Edge &e=edges[G[x][i]];
if(d[e.to]==d[x]+ && (f=DFS(e.to,min(a,e.cap-e.flow) ) )>)
{
e.flow +=f;
edges[G[x][i]^].flow -=f;
flow +=f;
a -=f;
if(a==) break;
}
}
return flow;
} int max_flow()
{
int ans=;
while(BFS())
{
memset(cur,,sizeof(cur));
ans +=DFS(s,INF);
}
return ans;
}
}DC; int full_flow; int main()
{
int T; scanf("%d",&T);
for(int kase=;kase<=T;++kase)
{
int n,m;
scanf("%d%d",&n,&m);
full_flow=;
int src=,dst=+n+;
DC.init(++n,src,dst);
bool vis[maxn];//表示第i天是否被用到
memset(vis,,sizeof(vis)); for(int i=;i<=n;++i)
{
int P,S,E;
scanf("%d%d%d",&P,&S,&E);
DC.AddEdge(src,+i,P);
full_flow += P;
for(int j=S;j<=E;++j)
{
DC.AddEdge(+i,j,);
vis[j]=true;
}
} for(int i=;i<=;++i)if(vis[i])//被任务覆盖的日子才添加边
DC.AddEdge(i,dst,m);
printf("Case %d: %s\n\n",kase,DC.max_flow()==full_flow?"Yes":"No");
}
return ;
}
上一篇:数据库MySQL——安装


下一篇:JVM性能调优监控工具jps、jstack、jmap、jhat、jstat、hprof