hdu 3572 Task Schedule 最大流 Dinic算法,,卡时间。。建图非常有讲究

Task Schedule

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)

Total Submission(s): 4617    Accepted Submission(s): 1513

Problem Description

Our geometry princess XMM has stoped her study in computational geometry to concentrate on her newly opened factory. Her factory has introduced M new machines in order to process the coming N tasks. For the i-th task, the factory
has to start processing it at or after day Si, process it for Pi days, and finish the task before or at day Ei. A machine can only work on one task at a time, and each task can be processed by at most one machine at a time. However, a task can be interrupted
and processed on different machines on different days.

Now she wonders whether he has a feasible schedule to finish all the tasks in time. She turns to you for help.

Input

On the first line comes an integer T(T<=20), indicating the number of test cases.

You are given two integer N(N<=500) and M(M<=200) on the first line of each test case. Then on each of next N lines are three integers Pi, Si and Ei (1<=Pi, Si, Ei<=500), which have the meaning described in the description. It is guaranteed that in a feasible
schedule every task that can be finished will be done before or at its end day.

Output

For each test case, print “Case x: ” first, where x is the case number. If there exists a feasible schedule to finish all the tasks, print “Yes”, otherwise print “No”.

Print a blank line after each test case.

Sample Input

2
4 3
1 3 5
1 1 4
2 3 7
3 5 9

2 2
2 1 3
1 2 2

Sample Output

Case 1: Yes

Case 2: Yes

最大流。这个题的建图算是经典,因为限定每个时刻每台机器只能处理一个任务,所以可以把时间点分配给各个合法的机器...具体是先设定一个超级源点S,连向各个任务,容量为该任务所需时间,各个任务连向在范围内的时间点,容量为1(保证每个时刻xxx这个条件),所有时间点连向超级汇点T,容量为机器台数,最后求最大流,等于所有机器所需时间和的就是yes

代码:

#include <cstdio>
#include <cstring>
#include <queue>
#define SIZE 1100
#define INF 1000000000
using namespace std ;

struct Edge{
	int to , w , next ;
}edge[SIZE*SIZE];

int n , m , start , ends , index = 0;
int  head[SIZE] , level[SIZE] , cur[SIZE];
bool visited[SIZE] ;
bool bfs()
{
	queue<int> que ;
	que.push(start) ;
	memset(level,-1,sizeof(level)) ;
	level[start] = 0 ;
	while(!que.empty())
	{
		int pos = que.front() ;
		que.pop() ;
		for(int next = head[pos] ; next != -1 ; next = edge[next].next)
		{
			if(level[edge[next].to]<0 && edge[next].w>0)
			{
				level[edge[next].to] = level[pos]+1 ;
				que.push(edge[next].to) ;
			}
		}
	}
	return level[ends] != -1 ;
}
int min(int a , int b)
{
	return a>b?b:a ;
}
int dfs(int pos , int flow)
{
	int deta = 0 , tmp = 0;
	if(pos == ends)
		return flow ;
	for(int next = head[pos] ; next != -1 ; next = edge[next].next)
	{
		if(edge[next].w > 0 &&
			level[pos] == level[edge[next].to]-1)
				{
					tmp = dfs(edge[next].to,min(flow-deta,edge[next].w)) ;
					if(tmp>0)
					{
						edge[next].w -= tmp ;
						edge[next^1].w += tmp ;
						deta += tmp ;
						if(deta == flow)
							break ;
					}
					else
						level[edge[next].to] = -1 ;		//不加这个,,超时。。。
				}
	}
	return deta ;
}

int dinic()
{
	int ans = 0 , flow = 0 ;
	while(bfs())
	{
		int deta = 0 ;
		ans += dfs(0,INF) ;
	}
	return ans ;
}

void add(int s , int d , int w)
{
	edge[index].next = head[s] ;
	edge[index].to = d ;
	edge[index].w = w ;
	head[s] = index ++ ;

	edge[index].next = head[d] ;
	edge[index].to = s ;
	edge[index].w = 0 ;
	head[d] = index ++ ;
}

int main()
{
	int t , c = 1 ;
	scanf("%d",&t) ;
	while(t--)
	{
		scanf("%d%d",&n,&m) ;
		memset(head,-1,sizeof(head)) ;
		index = 0 ;
		int sum = 0 , max = -1;
		start = 0;
		for(int i = 1 ; i <= n ; ++i)
		{
			int x , y , z ;
			scanf("%d%d%d",&x,&y,&z) ;
			sum += x ;
			max = max>z?max:z ;
			add(start,i,x) ;
			for(int j = y ; j <= z ; ++j)
			{
				add(i,j+n,1) ;
			}
		}
		ends = n+max+1 ;
		for(int i = 1 ; i <= max ; ++i)
			add(i+n,ends,m) ;
		int ans = dinic() ;
		printf("Case %d: ",c++) ;
		if(ans != sum)
			puts("No\n") ;
		else
			puts("Yes\n");
	}
	return 0 ;
}

与君共勉

时间: 2024-10-14 13:09:45

hdu 3572 Task Schedule 最大流 Dinic算法,,卡时间。。建图非常有讲究的相关文章

HDU 3572 Task Schedule (最大流)

C - Task Schedule Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u Submit Status Practice HDU 3572 Description Our geometry princess XMM has stoped her study in computational geometry to concentrate on her newly opened fac

hdu 3572 Task Schedule(网络流 dinic算法)

Task Schedule Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 3412    Accepted Submission(s): 1197 Problem Description Our geometry princess XMM has stoped her study in computational geometry t

hdu 3572 Task Schedule(最大流)

hdu 3572 Task Schedule Description Our geometry princess XMM has stoped her study in computational geometry to concentrate on her newly opened factory. Her factory has introduced M new machines in order to process the coming N tasks. For the i-th tas

HDU 3572 Task Schedule(ISAP)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3572 题意:m台机器,需要做n个任务.第i个任务,你需要使用机器Pi天,且这个任务要在[Si  ,  Ei]区间内完成才有效.对于一个任务,只能由一个机器来完成,一个机器同一时间只能做一个任务.当然,一个任务可以分成几段不连续的时间来完成.问,能否做完全部任务. 题意很清晰,也就是判断是否是满流. 对于网络流问题,模板大家都有,关键在于如何建图(详见资料) 思路:今天问了龙哥,对建图有了一定的了解,

HDU 3572 Task Schedule(最大流Dinic算法)

该题非常经典,建图的方法非常巧妙,因为每个任务的完成不一定要连续,而且可以换机器完成,而且我们注意到时间点最多500,很小,所以我们将时间点抽出来建图. 对于每个任务,将其时间范围内的点与之连起来,容量显然为1 ,并与汇点相连,容量为p[i] .  对于每个时间点,因为最多可以有m台机器同时工作,所以容量为m . 一开始老想着任务和机器之间怎么建立联系了. 推荐题目: 点击打开链接 细节参见代码: #include<bits/stdc++.h> using namespace std; typ

HDU 3572 Task Schedule(拆点+最大流dinic)

Task Schedule Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 7753    Accepted Submission(s): 2381 Problem Description Our geometry princess XMM has stoped her study in computational geometry t

hdu 3572 Task Schedule (Dinic模板)

Problem Description Our geometry princess XMM has stoped her study in computational geometry to concentrate on her newly opened factory. Her factory has introduced M new machines in order to process the coming N tasks. For the i-th task, the factory

hdu 3572 Task Schedule【 最大流 】

求出最大流,再判断是否满流 先不理解为什么要这样建图 后来看了这一篇题解 http://blog.csdn.net/u012350533/article/details/12361003 把0看做源点st 把每一个任务看做一个点 st到每个任务连边,容量为p,表示任务完成需要的天数 每个任务到每个任务的开始至结束时间连边,容量为1,表示这个任务可以在这些天完成 每一天向汇点ed连边,容量为m,表示一天最多运行m个任务 然后判断最大流是否等于执行完所有任务所需要的时间 1 #include<cst

hdu 3572 Task Schedule

Task Schedule Problem Description Our geometry princess XMM has stoped her study in computational geometry to concentrate on her newly opened factory. Her factory has introduced M new machines in order to process the coming N tasks. For the i-th task