列表

详情


NC208166. 寻找未曾见过的你

描述

彼方为谁,无我有问。
九月露湿,待君之前。

在梦中,AR的灵魂被切割成了3部分,并且都被传送到了不同的次元空间。
这个次元空间可以用 <n,m> 来表示,有n个点,m条无向边。保证不同的次元空间n一定是相同的。
3个灵魂会在不同次元的同一个点苏醒,之后灵魂可以在图上任意游走(如果存在u连接v的边,则可以从u到v或者从v到u,或者原地不动),灵魂的移动速度可以假设为无穷大。
只有天亮的时候,3个灵魂停在同一个地方(编号相同的点),AR才可以苏醒。
你能帮AR计算一下,AR苏醒的方案数吗?
由于灵魂在次元空间苏醒的点是不一样的,所以你需要对每个点都求出,如果灵魂在这个点苏醒,AR苏醒的方案数。

输入描述

第一行输入4个整数:n,x,y,z。分别代表次元空间的点的个数,第一个次元空间的边的数量,第二个次元空间的边的数量,第三个次元空间的边的数量。
然后x行,每行2个整数:u,v。代表第一个次元的点u和点v互相连接。
然后y行,每行2个整数:u,v。代表第二个次元的点u和点v互相连接。
然后z行,每行2个整数:u,v。代表第三个次元的点u和点v互相连接。
1<=n<=5e5
0<=x<=n
0<=y<=n
0<=z<=n
1<=u<=n
1<=v<=n

输出描述

输出有n行。
第i行代表如果灵魂从点i苏醒,AR苏醒的方案数。

示例1

输入:

3 2 2 1
1 2
2 3
1 2
2 3
1 3

输出:

2
1
2

说明:

如果在点1苏醒,那么可以三个灵魂都去点1或者点3。故方案数为2
如果在点2苏醒,那么三个灵魂只能都在点2.故方案数为1

原站题解

上次编辑到这里,代码来自缓存 点击恢复默认模板

C++11(clang++ 3.9) 解法, 执行用时: 1524ms, 内存消耗: 82648K, 提交时间: 2020-06-25 19:08:54

#include<bits/stdc++.h>
using namespace std;

map<int,map<int,map<int,int>>>T;
int V[3][500005];
int find(int i,int a)
{
	if(V[i][a]==a)return a;
	return V[i][a]=find(i,V[i][a]);
}
int main()
{
    int i,j,a,b,n,x,y,z;
    scanf("%d%d%d%d",&n,&x,&y,&z);
    for(i=1;i<=n;i++)V[0][i]=V[1][i]=V[2][i]=i;
    while(x--)
    {
    	scanf("%d%d",&i,&j);
    	a=find(0,i),b=find(0,j);
    	if(a!=b)V[0][a]=b;
	}
	while(y--)
    {
    	scanf("%d%d",&i,&j);
    	a=find(1,i),b=find(1,j);
    	if(a!=b)V[1][a]=b;
	}
	while(z--)
    {
    	scanf("%d%d",&i,&j);
    	a=find(2,i),b=find(2,j);
    	if(a!=b)V[2][a]=b;
	}
	for(i=1;i<=n;i++)x=find(0,i),y=find(1,i),z=find(2,i),T[x][y][z]++;
	for(i=1;i<=n;i++)
	{
		x=find(0,i),y=find(1,i),z=find(2,i);
		printf("%d\n",T[x][y][z]);
	}
}

C++14(g++5.4) 解法, 执行用时: 1487ms, 内存消耗: 71400K, 提交时间: 2020-06-22 17:15:19

#include<bits/stdc++.h>
using namespace std;
const int N = 5e5+5;
vector<int>adj[N];
long long type[N];
int n, m[3], u, v, space;
void DFS(int cur, int root)
{
	if(type[cur]>>(20*space) & 0xfffff)
		return;
	type[cur] |= root * 1LL << (20*space);
	for(auto r : adj[cur])
		DFS(r, root);
}
int main()
{
	ios::sync_with_stdio(0);
	cin >> n >> m[0] >> m[1] >> m[2];
	for(space = 0; space < 3; space++)
	{
		for(int i = 1; i <= n; i++)
			adj[i].clear();
		for(int i = 0; i < m[space]; i++)
		{
			cin >> u >> v;
			adj[u].push_back(v);
			adj[v].push_back(u);
		}
		for(int i = 1; i <= n; i++)
			DFS(i, i);	
	}
	map<long long, int>mp;
	for(int i = 1; i <= n; i++)
		mp[type[i]]++;
	for(int i = 1; i <= n; i++)
		cout << mp[type[i]] << endl;
}

上一题