cf1041E

题意:要求你构造一棵树,树中每一个节点都有一个编号(互不相同),告诉你删除掉每一条边之后的两个联通分量中节点标号的最大值,要求你输出这颗树,不存在就输出NO

题解:可以发现这颗树实际上是一个序列,我们构造一个序列就可以了

#include<bits/stdc++.h>

using namespace std;

const int N = 200043;

int cnt[N];

int main()
{                
	int n;
	scanf("%d", &n);
	for(int i = 0; i < n - 1; i++)
	{
		int x, y;
		scanf("%d %d", &x, &y);
		if(y != n)
		{
			puts("NO");
			return 0;
		}
		cnt[x]++;
	}
	int cur = 0;
	for(int i = 1; i < n; i++)
	{
		cur += cnt[i];
		if(cur > i)
		{
			puts("NO");
			return 0;
		}
	}
	int last = -1;
	puts("YES");
	set<int> unused;
	for(int i = 1; i < n; i++)
		unused.insert(i);
	for(int i = 1; i < n; i++)
	{
		if(cnt[i] > 0)
		{
			unused.erase(i);
			if(last != -1)
				printf("%d %d\n", last, i);
			last = i;
			cnt[i]--;
		}
		while(cnt[i] > 0)
		{
			printf("%d %d\n", last, *unused.begin());
			last = *unused.begin();
			cnt[i]--;
			unused.erase(unused.begin());
		}
	}
	printf("%d %d\n", last, n);
}

  

posted on 2020-02-21 21:29  欣崽  阅读(203)  评论(0编辑  收藏  举报

导航