POJ 2455 Secret Milking Machine(二分+最大流)

POJ 2455 Secret Milking Machine

题目链接

题意:一个无向图,要求有T条不重复道路可以从1走到t,问道路中最大边的最小值可以是多少

思路:二分+最大流,二分长度,连起边,注意是无向图,所以反向边是有容量的,然后源点和1连容量t,n和汇点连容量是t

代码:

#include <cstdio>
#include <cstring>
#include <queue>
#include <algorithm>
using namespace std;

const int MAXNODE = 205;
const int MAXEDGE = 100005;

typedef int Type;
const Type INF = 0x3f3f3f3f;

struct Edge {
	int u, v;
	Type cap, flow;
	Edge() {}
	Edge(int u, int v, Type cap, Type flow) {
		this->u = u;
		this->v = v;
		this->cap = cap;
		this->flow = flow;
	}
};

struct Dinic {
	int n, m, s, t;
	Edge edges[MAXEDGE];
	int first[MAXNODE];
	int next[MAXEDGE];
	bool vis[MAXNODE];
	Type d[MAXNODE];
	int cur[MAXNODE];
	vector<int> cut;

	void init(int n) {
		this->n = n;
		memset(first, -1, sizeof(first));
		m = 0;
	}
	void add_Edge(int u, int v, Type cap) {
		edges[m] = Edge(u, v, cap, 0);
		next[m] = first[u];
		first[u] = m++;
		edges[m] = Edge(v, u, cap, 0);
		next[m] = first[v];
		first[v] = m++;
	}

	bool bfs() {
		memset(vis, false, sizeof(vis));
		queue<int> Q;
		Q.push(s);
		d[s] = 0;
		vis[s] = true;
		while (!Q.empty()) {
			int u = Q.front(); Q.pop();
			for (int i = first[u]; i != -1; i = next[i]) {
				Edge& e = edges[i];
				if (!vis[e.v] && e.cap > e.flow) {
					vis[e.v] = true;
					d[e.v] = d[u] + 1;
					Q.push(e.v);
				}
			}
		}
		return vis[t];
	}

	Type dfs(int u, Type a) {
		if (u == t || a == 0) return a;
		Type flow = 0, f;
		for (int &i = cur[u]; i != -1; i = next[i]) {
			Edge& e = edges[i];
			if (d[u] + 1 == d[e.v] && (f = dfs(e.v, min(a, e.cap - e.flow))) > 0) {
				e.flow += f;
				edges[i^1].flow -= f;
				flow += f;
				a -= f;
				if (a == 0) break;
			}
		}
		return flow;
	}

	Type Maxflow(int s, int t) {
		this->s = s; this->t = t;
		Type flow = 0;
		while (bfs()) {
			for (int i = 0; i < n; i++)
				cur[i] = first[i];
			flow += dfs(s, INF);
		}
		return flow;
	}

	void MinCut() {
		cut.clear();
		for (int i = 0; i < m; i += 2) {
			if (vis[edges[i].u] && !vis[edges[i].v])
				cut.push_back(i);
		}
	}
} gao;

const int N = 40005;
int n, p, t;
int u[N], v[N], w[N];

bool judge(int len) {
	gao.init(n + 2);
	gao.add_Edge(0, 1, t);
	for (int i = 0; i < p; i++) {
		if (w[i] > len) continue;
		gao.add_Edge(u[i], v[i], 1);
	}
	gao.add_Edge(n, n + 1, t);
	return gao.Maxflow(0, n + 1) == t;
}

int main() {
	while (~scanf("%d%d%d", &n, &p, &t)) {
		int l = 0, r = 0;
		for (int i = 0; i < p; i++) {
			scanf("%d%d%d", &u[i], &v[i], &w[i]);
			r = max(r, w[i]);
		}
		while (l < r) {
			int mid = (l + r) / 2;
			if (judge(mid)) r = mid;
			else l = mid + 1;
		}
		printf("%d\n", l);
	}
	return 0;
}
时间: 2024-10-26 05:26:53

POJ 2455 Secret Milking Machine(二分+最大流)的相关文章

POJ 2455 Secret Milking Machine (二分 + 最大流)

题目大意: 给出一张无向图,找出T条从1..N的路径,互不重复,求走过的所有边中的最大值最小是多少. 算法讨论: 首先最大值最小就提醒我们用二分,每次二分一个最大值,然后重新构图,把那些边权符合要求的边加入新图,在新图上跑网络流. 这题有许多注意的地方: 1.因为是无向图,所以我们在加正向边和反向边的时候,流量都是1,而不是正向边是1,反向边是0. 2.题目中说这样的路径可能不止t条,所以我们在最后二分判定的时候不能写 == t,而是要 >= t. 3.这题很容易T ,表示我T了N遍,弱菜啊.

POJ 2455 Secret Milking Machine(搜索-二分,网络流-最大流)

Secret Milking Machine Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 9658   Accepted: 2859 Description Farmer John is constructing a new milking machine and wishes to keep it secret as long as possible. He has hidden in it deep within

poj 2455 Secret Milking Machine 【二分 + 最大流】 【1到N不重复路径不少于T条时,求被选中路径上的最大边权值 的最小值】

Secret Milking Machine Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 10620   Accepted: 3110 Description Farmer John is constructing a new milking machine and wishes to keep it secret as long as possible. He has hidden in it deep within

poj 2455 Secret Milking Machine

[题意]:(半天没懂题目什么意思,诶..)FJ有N块地,这些地之间有P条双向路,每条路的都有固定的长度l.现在要你找出从第1块地到第n块地的T条不同路 径,每条路径上的路不能与先前的路径重复,问这些路径中的最长路的最小是多少. [思路]二分判定最长路的最小值,再用小于这个值的边建图跑最大流.建图的话,整张无向图(记得是无向图! 对一条边正向方向都要添加wa 好久  )加一个源点和点1 连边容量无穷大,n点和会汇点连边,容量无穷大,最大流是多少能够找到的不同的路径就是多少. 1 #include<

POJ 2112 Optimal Milking(二分+最大流)

POJ 2112 Optimal Milking 题目链接 题意:给定一些机器和奶牛,在给定距离矩阵,(不在对角线上为0的值代表不可达),每个机器能容纳m个奶牛,问所有奶牛都能挤上奶,那么走的距离最大的奶牛的最小值是多少 思路:明显的二分+最大流,注意floyd求出的距离矩阵最大值可能不止200,所以二分的上限要注意 代码: #include <cstdio> #include <cstring> #include <queue> #include <algori

【bzoj1733】[Usaco2005 feb]Secret Milking Machine 神秘的挤奶机 二分+网络流最大流

题目描述 Farmer John is constructing a new milking machine and wishes to keep it secret as long as possible. He has hidden in it deep within his farm and needs to be able to get to the machine without being detected. He must make a total of T (1 <= T <=

[bzoj1733][Usaco2005 feb]Secret Milking Machine 神秘的挤奶机_网络流

[Usaco2005 feb]Secret Milking Machine 神秘的挤奶机 题目大意:约翰正在制造一台新型的挤奶机,但他不希望别人知道.他希望尽可能久地隐藏这个秘密.他把挤奶机藏在他的农场里,使它不被发现.在挤奶机制造的过程中,他需要去挤奶机所在的地方T(1≤T≤200)次.他的农场里有秘密的地道,但约翰只在返回的时候用它.农场被划分成N(2≤N≤200)块区域,用1到200标号.这些区域被P(1≤P≤40000)条道路连接,每条路有一个小于10^6的长度L.两块区域之间可能有多条

POJ2455 Secret Milking Machine【二分,最大流】

题目大意:N个点P条边,令存在T条从1到N的路径,求路径上的边权的最大值最小为多少 思路:做了好多二分+最大流的题了,思路很好出 二分出最大边权后建图,跑dinic 问题是....这题是卡常数的好题!!!!! T了8发以后实在受不了,瞄了眼网上的程序,齐刷刷的邻接矩阵....论邻接矩阵的优越性 但不信邪的我终于反复优化常数后邻接表A了 //TLE的程序 #include <stdio.h> #include <iostream> #include <string.h>

POJ 2112 Optimal Milking (二分 + floyd + 网络流)

POJ 2112 Optimal Milking 链接:http://poj.org/problem?id=2112 题意:农场主John 将他的K(1≤K≤30)个挤奶器运到牧场,在那里有C(1≤C≤200)头奶牛,在奶牛和挤奶器之间有一组不同长度的路.K个挤奶器的位置用1-K的编号标明,奶牛的位置用K+1-K+C 的编号标明.每台挤奶器每天最多能为M(1≤M≤15)头奶牛挤奶.寻找一个方案,安排每头奶牛到某个挤奶器挤奶,并使得C 头奶牛需要走的所有路程中的最大路程最小.每个测试数据中至少有一