#pragma GCC optimize("Ofast", "unroll-loops")

#include <bits/stdc++.h>

using namespace std;

#define ll long long
#define ld long double

using p = pair<int, int>;

int main(void){
	int N; cin >> N;
	vector<p> U, R, D, L;
	for (int i = 0; i < N; ++i){
		int X, Y; char d;
		cin >> X >> Y >> d;
		if (d == 'U') U.push_back({X, Y});
		else if (d == 'R') R.push_back({X, Y});
		else if (d == 'D') D.push_back({X, Y});
		else L.push_back({X, Y});
	}

	int res = (1 << 30); // INF

	{ // UとDの衝突
		map<int, vector<int>> UXY, DXY;
		for (p pl : U) UXY[pl.first].push_back(pl.second);
		for (p pl : D) DXY[pl.first].push_back(pl.second);
		for (auto& e : UXY)
			sort(e.second.begin(), e.second.end());
		for (auto& e : DXY)
			sort(e.second.begin(), e.second.end());
		for (auto& e : UXY){
			int X = e.first;
			for (int Y : e.second){
				auto iter = lower_bound(DXY[X].begin(), DXY[X].end(), Y);
				if (iter == DXY[X].end()) continue;
				else res = min(res, ((*iter) - Y) * 5);
			}
		}
	}

	{ // RとLの衝突
		map<int, vector<int>> RXY, LXY;
		for (p pl : R) RXY[pl.second].push_back(pl.first);
		for (p pl : L) LXY[pl.second].push_back(pl.first);
		for (auto& e : RXY)
			sort(e.second.begin(), e.second.end());
		for (auto& e : LXY)
			sort(e.second.begin(), e.second.end());
		for (auto& e : RXY){
			int Y = e.first;
			for (int X : e.second){
				auto iter = lower_bound(LXY[Y].begin(), LXY[Y].end(), X);
				if (iter == LXY[Y].end()) continue;
				else res = min(res, ((*iter) - X) * 5);
			}
		}
	}

	{ // RとUの衝突
		map<int, vector<int>> RsX, UsX;
		for (auto pl : R) RsX[pl.first + pl.second].push_back(pl.first);
		for (auto pl : U) UsX[pl.first + pl.second].push_back(pl.first);
		for (auto& e : RsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : UsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : RsX){
			int s = e.first;
			for (int X : e.second){
				auto iter = lower_bound(UsX[s].begin(), UsX[s].end(), X);
				if (iter == UsX[s].end()) continue;
				else res = min(res, ((*iter) - X) * 10);
			}
		}
	} 

	// RとDの衝突
	{
		map<int, vector<int>> RsX, DsX;
		for (auto pl : R) RsX[pl.first - pl.second].push_back(pl.first);
		for (auto pl : D) DsX[pl.first - pl.second].push_back(pl.first);
		for (auto& e : RsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : DsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : RsX){
			int s = e.first;
			for (int X : e.second){
				auto iter = lower_bound(DsX[s].begin(), DsX[s].end(), X);
				if (iter == DsX[s].end()) continue;
				else res = min(res, ((*iter) - X) * 10);
			}
		}
	}

	// LとUの衝突
	{
		map<int, vector<int>> UsX, LsX;
		for (auto pl : U) UsX[pl.first - pl.second].push_back(pl.first);
		for (auto pl : L) LsX[pl.first - pl.second].push_back(pl.first);
		for (auto& e : UsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : LsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : UsX){
			int s = e.first;
			for (int X : e.second){
				auto iter = lower_bound(LsX[s].begin(), LsX[s].end(), X);
				if (iter == LsX[s].end()) continue;
				else res = min(res, ((*iter) - X) * 10);
			}
		}
	}

	// LとDの衝突
	{
		map<int, vector<int>> DsX, LsX;
		for (auto pl : D) DsX[pl.first + pl.second].push_back(pl.first);
		for (auto pl : L) LsX[pl.first + pl.second].push_back(pl.first);
		for (auto& e : DsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : LsX)
			sort(e.second.begin(), e.second.end());
		for (auto& e : DsX){
			int s = e.first;
			for (int X : e.second){
				auto iter = lower_bound(LsX[s].begin(), LsX[s].end(), X);
				if (iter == LsX[s].end()) continue;
				else res = min(res, ((*iter) - X) * 10);
			}
		}
	}

	if (res == (1 << 30)) cout << "SAFE" << endl;
	else cout << res << endl;

	return 0;
}

Measured memory_bytes: 41972