Submission #167505

# Submission time Handle Problem Language Result Execution time Memory
167505 2019-12-08T18:01:28 Z faremy Parachute rings (IOI12_rings) C++14
0 / 100
1366 ms 86748 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() > 2 || 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;
}
# Verdict Execution time Memory Grader output
1 Correct 24 ms 23800 KB Output is correct
2 Correct 27 ms 24060 KB Output is correct
3 Correct 28 ms 24088 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24056 KB Output is correct
6 Correct 27 ms 24312 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 24176 KB Output isn't correct
# Verdict Execution time Memory Grader output
1 Correct 452 ms 44792 KB Output is correct
2 Correct 976 ms 56944 KB Output is correct
3 Correct 1105 ms 60152 KB Output is correct
4 Correct 1215 ms 64904 KB Output is correct
5 Correct 1240 ms 65912 KB Output is correct
6 Correct 1366 ms 86748 KB Output is correct
7 Correct 1042 ms 59492 KB Output is correct
8 Correct 1135 ms 62500 KB Output is correct
9 Incorrect 1244 ms 65372 KB Output isn't correct
10 Halted 0 ms 0 KB -
# Verdict Execution time Memory Grader output
1 Correct 24 ms 23800 KB Output is correct
2 Correct 27 ms 24060 KB Output is correct
3 Correct 28 ms 24088 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24056 KB Output is correct
6 Correct 27 ms 24312 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 24176 KB Output isn't correct
# Verdict Execution time Memory Grader output
1 Correct 24 ms 23800 KB Output is correct
2 Correct 27 ms 24060 KB Output is correct
3 Correct 28 ms 24088 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24056 KB Output is correct
6 Correct 27 ms 24312 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 24176 KB Output isn't correct
# Verdict Execution time Memory Grader output
1 Correct 24 ms 23800 KB Output is correct
2 Correct 27 ms 24060 KB Output is correct
3 Correct 28 ms 24088 KB Output is correct
4 Correct 25 ms 23928 KB Output is correct
5 Correct 26 ms 24056 KB Output is correct
6 Correct 27 ms 24312 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 24176 KB Output isn't correct