Submission #427239

#TimeUsernameProblemLanguageResultExecution timeMemory
427239frodakcinRail (IOI14_rail)C++17
30 / 100
101 ms748 KiB
#include "rail.h"
#include <cstdio>
#include <vector>
#include <algorithm>
#include <functional>
#include <map>

const int INF = 0x3f3f3f3f;

bool ckmin(auto& a, const auto& b) {return b<a?a=b,1:0;}

struct appl // apparent location
{
	public:
		int i, x;
		appl(int _i=-1, int _x=0): i(_i), x(_x) {}
		bool operator < (const appl& o) const {return x < o.x;}
		bool operator > (const appl& o) const {return x > o.x;}
};

void findLocation(int N, int first, int location[], int stype[])
{
	int A=0, B, bestd=INF;
	std::map<int, int> map;
	auto add=[&](int u){map[location[u]]=stype[u];};
	std::vector<int> da(N), db(N);
	for(int i=1;i<N;++i)
	{
		da[i]=getDistance(A, i);
		if(ckmin(bestd, da[i]))
			B=i;
	}

	location[A] = first;
	stype[A] = 1;
	add(A);
	location[B] = first + da[B];
	stype[B] = 2;
	add(B);

	std::vector<appl> left, right;
	int AB = da[B];
	int dbmin = da[B];
	for(int i=0;i<N;++i)
		if(i != A && i != B)
		{
			db[i] = getDistance(B, i);
			ckmin(dbmin, db[i]);
			if(db[i] < AB)
				location[i] = location[B]-db[i], stype[i]=1, add(i);
			else // outside range: to left or to right?
			{
				if(db[i] == da[i]-AB) // left
					left.push_back({i, location[B]-db[i]});
				else
					right.push_back({i, location[A]+da[i]});
			}
		}
	std::sort(left.begin(), left.end(), std::greater<appl>());
	std::sort(right.begin(), right.end());

	{
		appl prev(-1,0);
		int v, m;
		auto it = map.end();
		for(auto n:left)
		{
			bool ok=0;
			if(prev.i==-1 ||
					(v=getDistance(prev.i, n.i))+prev.x >= location[A] ||
					(m=v+prev.x+n.x)&1 ||
					(it=map.find(m/2))==map.end() ||
					it->second != 1)
			{
				prev=n;
				location[n.i]=n.x;
				stype[n.i]=1;
				add(n.i);
			}
			else
			{
				location[n.i]=prev.x+v;
				stype[n.i]=2;
				add(n.i);
			}
		}
	}

	{
		appl prev(-1,0);
		int v, m;
		auto it=map.end();
		for(auto n:right)
			if(prev.i==-1 ||
					prev.x-(v=getDistance(prev.i, n.i)) <= location[B] ||
					(m=prev.x-v+n.x)&1 || 
					(it=map.find(m/2)) == map.end() ||
					it->second != 2)
			{
				prev=n;
				location[n.i]=n.x;
				stype[n.i]=2;
				add(n.i);
			}
			else
			{
				location[n.i]=prev.x-v;
				stype[n.i]=1;
				add(n.i);
			}
	}

	//for(int i=0;i<N;++i) printf("%d %d\n", stype[i], location[i]);
}

Compilation message (stderr)

rail.cpp:10:12: warning: use of 'auto' in parameter declaration only available with '-fconcepts-ts'
   10 | bool ckmin(auto& a, const auto& b) {return b<a?a=b,1:0;}
      |            ^~~~
rail.cpp:10:27: warning: use of 'auto' in parameter declaration only available with '-fconcepts-ts'
   10 | bool ckmin(auto& a, const auto& b) {return b<a?a=b,1:0;}
      |                           ^~~~
rail.cpp: In function 'void findLocation(int, int, int*, int*)':
rail.cpp:68:9: warning: unused variable 'ok' [-Wunused-variable]
   68 |    bool ok=0;
      |         ^~
rail.cpp:37:28: warning: 'B' may be used uninitialized in this function [-Wmaybe-uninitialized]
   37 |  location[B] = first + da[B];
      |                            ^
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...