Dynamic Graph (dp,bitset)

链接:https://ac.nowcoder.com/acm/contest/1110/D
来源:牛客网
 

时间限制:C/C++ 1秒,其他语言2秒
空间限制:C/C++ 32768K,其他语言65536K
Special Judge, 64bit IO Format: %lld

题目描述

Bobo has a directed acyclic graph (DAG) with n nodes and m edges whose nodes is conveniently labeled with 1,2,…,n1, 2, \dots, n1,2,…,n.
All nodes are white initially.

Bobo performs q operations subsequently.
The i-th operation is to change the node viv_ivi​ from white to black or vice versa.

After each operation, he would like to know the number of pairs of nodes (u, v) that u, v are both white and there exists a path from u to v passing only white nodes.

输入描述:

The input contains zero or more test cases and is terminated by end-of-file. For each test case:
The first line contains three integers n, m and q.
The i-th of the following m lines contains two integers ai,bia_i, b_iai​,bi​.
The i-th of the last q lines contains an integer viv_ivi​.

* 2≤n≤3002 \leq n \leq 3002≤n≤300
* 1≤m≤n(n−1)21 \leq m \leq \frac{n(n - 1)}{2}1≤m≤2n(n−1)​
* 1≤q≤3001 \leq q \leq 3001≤q≤300
* 1≤ai<bi≤n1 \leq a_i < b_i \leq n1≤ai​<bi​≤n
* 1≤vi≤n1 \leq v_i \leq n1≤vi​≤n
* The number of tests cases does not exceed 10.

输出描述:

For each operation, output an integer which denotes the number of pairs.

示例1

输入

复制

3 3 2
2 3
1 3
1 2
1
1

输出

复制

1
3

              树形dp,bitset优化:子节点能够到达的点也是父节点能够到达的节点(非黑的时候),用bitset来统计。

#include<bits/stdc++.h>
using namespace std;
const int MAXN = 300 + 9;
int n, m, q, deg[MAXN], vis[MAXN], color[MAXN];
bitset<MAXN> p[MAXN];
vector<int> g[MAXN];
void dfs(int x) {
	if (vis[x]) return;
	vis[x] = 1;
	p[x].reset();
	for (auto e : g[x]) {
		dfs(e);
		if (!color[x] && !color[e])
			p[x] |= p[e], p[x][e] = 1;
	}
}
int main() {
	while (scanf("%d%d%d", &n, &m, &q) == 3) {
		for (int i = 1; i <= n; i++)
			g[i].clear(), deg[i] = color[i] = 0;
		for (int i = 0, u, v; i < m; i++) {
			scanf("%d%d", &u, &v);
			g[u].push_back(v);
			deg[v]++;
		}
		while (q--) {
			int x;
			scanf("%d", &x);
			color[x] ^= 1;
			memset(vis, 0, sizeof vis);
			for (int i = 1; i <= n; i++)
				if (deg[i] == 0) dfs(i);
			int ans = 0;
			for (int i = 1; i <= n; i++)
				ans += p[i].count();
			printf("%d\n", ans);
		}
	}

	return 0;
}

猜你喜欢

转载自blog.csdn.net/chenshibo17/article/details/102165384
今日推荐