답안 #167509

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
167509 2019-12-08T18:03:31 Z faremy 낙하산 고리들 (IOI12_rings) C++14
0 / 100
1318 ms 86892 KB
#include <algorithm>
#include <vector>
#include <iostream>


const int MAXN = 1e6;
int rings;

std::vector<int> graph[MAXN];
int parent[MAXN];
int ccSize[MAXN];

int candidate = -1;
int part = 0;
int last = -1;
bool isParticular[MAXN];

std::vector<int> listThree;
std::vector<int> listMore;
bool seen[MAXN];


void Init(int N_)
{
	rings = N_;
	for (int iRing = 0; iRing < rings; iRing++)
	{
		parent[iRing] = iRing;
		ccSize[iRing] = 1;
	}
}

int find(int node)
{
	if (node != parent[node])
		parent[node] = find(parent[node]);
	return parent[node];
}

void fillLists(int node)
{
	if (seen[node])
		return;
	seen[node] = true;

	if (graph[node].size() == 3)
		listThree.emplace_back(node);
	else if (graph[node].size() > 3)
		listMore.emplace_back(node);
	for (int next : graph[node])
		fillLists(next);
}

int nogood(int node, int root)
{
	if (seen[node])
		return 0;
	seen[node] = true;

	int degOffset = 0;
	for (int next : graph[node])
		if (next == root)
			degOffset = 1;

	if (graph[node].size() - degOffset == 3)
		return -1;
	
	int ans = (graph[node].size() - degOffset < 2);

	for (int next : graph[node])
	{
		int sub = nogood(next, root);
		if (sub == -1)
			return -1;
		ans |= sub;
	}

	return ans;
}

int check(int node)
{
	listThree.clear();
	listMore.clear();
	std::fill_n(seen, rings, false);

	fillLists(node);
	if (listThree.empty() && listMore.empty())
		return ccSize[node];

	if (listThree.size() > 3 || listMore.size() > 1 || (listMore.size() == 1 && listThree.size() > 0))
	{
		candidate = -2;
		return 0;
	}

	if (listMore.size() == 1)
	{
		std::fill_n(seen, rings, false);
		seen[listMore[0]] = true;
		
		for (int start : graph[listMore[0]])
			if (!seen[start] && nogood(start, listMore[0]) < 1)
			{
				candidate = -2;
				return 0;
			}

		return 1;
	}

	if (listThree.size() == 1)
	{
		std::fill_n(seen, rings, false);
		seen[listThree[0]] = true;

		int cyc = 0;
		for (int start : graph[listThree[0]])
		{
			if (seen[start])
				cyc++;
			else if (nogood(start, listThree[0]) < 1)
			{
				candidate = -2;
				return 0;
			}
		}

		if (cyc == 0)
			return 4;
		if (cyc == 1)
			return 3;
		return 1;
	}

	int ans = 0;
	for (int root : listThree)
	{	
		std::fill_n(seen, rings, false);
		seen[root] = true;

		bool isInvalid = false;
		for (int start : graph[root])
			if (!seen[start])
				isInvalid |= (nogood(start, root) < 1);
		ans += !isInvalid;
	}

	if (ans == 0)
		candidate = -2;
	return ans;
}

void Link(int A, int B)
{
	if (candidate == -2)
		return;
	int ccA = find(A);
	int ccB = find(B);

	graph[A].emplace_back(B);
	graph[B].emplace_back(A);

	if (ccA == ccB)
	{
		part += !isParticular[ccA];
		isParticular[ccA] = true;
		last = -1;
	}
	else
	{
		if (ccSize[ccA] < ccSize[ccB])
			std::swap(ccA, ccB);
		parent[ccB] = ccA;
		ccSize[ccA] += ccSize[ccB];

		if (isParticular[ccA] && isParticular[ccB])
		{
			part--;
			last = -1;
		}

		isParticular[ccA] |= isParticular[ccB];
		if (graph[A].size() == 3 || graph[A].size() == 4 || graph[B].size() == 3 || graph[B].size() == 4)
		{
			part += !isParticular[ccA];
			isParticular[ccA] = true;
			last = -1;
		}
		else if (graph[A].size() > 4 || graph[B].size() > 4)
		{
			isParticular[ccA] = true;
		}
	}

	if (isParticular[ccA] && candidate != -2)
		candidate = ccA;
}

int CountCritical()
{
	if (candidate == -2)
		return 0;
	if (part == 0)
		return rings;
	if (part > 1)
		return 0;
	//if (last == -1)
		last = check(candidate);
	return last;
}
# 결과 실행 시간 메모리 Grader output
1 Correct 25 ms 23776 KB Output is correct
2 Correct 26 ms 24056 KB Output is correct
3 Correct 27 ms 24056 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24104 KB Output is correct
6 Correct 28 ms 24320 KB Output is correct
7 Correct 25 ms 23928 KB Output is correct
8 Correct 26 ms 24056 KB Output is correct
9 Correct 27 ms 24184 KB Output is correct
10 Incorrect 27 ms 24128 KB Output isn't correct
# 결과 실행 시간 메모리 Grader output
1 Correct 458 ms 45176 KB Output is correct
2 Correct 973 ms 57324 KB Output is correct
3 Correct 1093 ms 60244 KB Output is correct
4 Correct 1225 ms 65324 KB Output is correct
5 Correct 1203 ms 66224 KB Output is correct
6 Correct 1318 ms 86892 KB Output is correct
7 Correct 1052 ms 59680 KB Output is correct
8 Correct 1130 ms 62668 KB Output is correct
9 Incorrect 1294 ms 65608 KB Output isn't correct
10 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Correct 25 ms 23776 KB Output is correct
2 Correct 26 ms 24056 KB Output is correct
3 Correct 27 ms 24056 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24104 KB Output is correct
6 Correct 28 ms 24320 KB Output is correct
7 Correct 25 ms 23928 KB Output is correct
8 Correct 26 ms 24056 KB Output is correct
9 Correct 27 ms 24184 KB Output is correct
10 Incorrect 27 ms 24128 KB Output isn't correct
# 결과 실행 시간 메모리 Grader output
1 Correct 25 ms 23776 KB Output is correct
2 Correct 26 ms 24056 KB Output is correct
3 Correct 27 ms 24056 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24104 KB Output is correct
6 Correct 28 ms 24320 KB Output is correct
7 Correct 25 ms 23928 KB Output is correct
8 Correct 26 ms 24056 KB Output is correct
9 Correct 27 ms 24184 KB Output is correct
10 Incorrect 27 ms 24128 KB Output isn't correct
# 결과 실행 시간 메모리 Grader output
1 Correct 25 ms 23776 KB Output is correct
2 Correct 26 ms 24056 KB Output is correct
3 Correct 27 ms 24056 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24104 KB Output is correct
6 Correct 28 ms 24320 KB Output is correct
7 Correct 25 ms 23928 KB Output is correct
8 Correct 26 ms 24056 KB Output is correct
9 Correct 27 ms 24184 KB Output is correct
10 Incorrect 27 ms 24128 KB Output isn't correct