Într-un oraș există un hotel de formă cubică, cu N
etaje, numerotate de la 1
la N
. Suprafața fiecărui etaj K
(1 ≤ K ≤ N
) este pătratică și este împărțită în N x N
camere identice alăturate, dispuse pe N
linii și N
coloane, fiecare cameră având drept etichetă un triplet de numere naturale (K L C
) (K=
etajul, L=
linia, C=
coloana, 1 ≤ L, C ≤ N
), ca în imaginea alăturată.
Dintre cele N x N x N
camere ale hotelului, una este specială deoarece în ea locuiește de mult timp un șoricel. Fiind isteț, el știe eticheta camerei în care se află precum și eticheta camerei în care bucătarul hotelului depozitează alimente.
Studiind hotelul, șoricelul a constatat că pe fiecare etaj, din orice cameră poate intra în toate camerele care au un perete comun cu aceasta (existând un mic orificiu pentru aerisire).
De asemenea, șoricelul a constatat că din fiecare cameră (situată la etajele 2
, 3
, …, sau N-1
) poate intra în camera situată imediat deasupra ei și în camera situată imediat sub ea.
Fiind un șoricel binecrescut, el nu intră în nicio cameră ocupată de clienți ca să nu-i deranjeze. Hotelul având mulți clienți, șoricelul trebuie să-și găsească cel mai scurt traseu de la camera lui la camera cu alimente, traseu care să treacă printr-un număr minim de camere, toate neocupate.
Cerinţe:
Se cere să se determine:
Exemplu
traseu.in
3 4 1 1 1 3 3 3 3 3 1 2 1 1 3 1 1 3 1 3
traseu.out
7 1 1 1 1 1 2 1 1 3 1 2 3 1 3 3 2 3 3 3 3 3
Explicație
Hotelul are trei etaje (1
, 2
şi 3
). Pe fiecare etaj sunt 3*3
camere. Șoricelul se află în camera cu eticheta (1 1 1)
iar camera cu alimente are eticheta (3 3 3)
.
Sunt 4
camere ocupate de clienţi. Acestea au etichetele : 3 3 1
, 2 1 1
, 3 1 1
, 3 1 3
.
Traseul cel mai scurt trece prin T=7
camere. Sunt mai multe astfel de trasee. De exemplu:
(1 1 1, 1 1 2, 1 1 3, 1 2 3, 1 3 3, 2 3 3, 3 3 3)
(1 1 1, 1 1 2, 1 1 3, 2 1 3, 2 2 3, 3 2 3, 3 3 3)
(1 1 1, 1 2 1, 1 3 1, 1 3 2, 2 3 2, 3 2 3, 3 3 3)
- etc.
Cel mai mic astfel de traseu (în sens lexicografic) este traseul 1).
#include <bits/stdc++.h> using namespace std; ifstream cin("traseu.in"); ofstream cout("traseu.out"); int di[] = {-1 , 0 , 0 , 0 , 0 , 1}; int dj[] = { 0 , -1 , 0 , 0 , 1 , 0}; int dk[] = { 0 , 0 , -1 , 1 , 0 , 0}; struct poz { int i , j , k; }; int a[101][101][101] , n , m; poz p1 , p2 , dr[1000001]; queue <poz> Q; bool inside(int i , int j , int k) { return i >= 1 && i <= n && j >= 1 && j <= n && k >= 1 && k <= n; } void lee(poz p) { Q.push(p); a[p.i][p.j][p.k] = 1; while(! Q.empty()) { p = Q.front(); for(int d = 0 ; d < 6 ; d++) { int inou = p.i + di[d]; int jnou = p.j + dj[d]; int knou = p.k + dk[d]; if(inside(inou , jnou , knou) && a[inou][jnou][knou] == 0) { poz pnou; pnou.i = inou; pnou.j = jnou; pnou.k = knou; Q.push(pnou); a[inou][jnou][knou] = a[p.i][p.j][p.k] + 1; } } Q.pop(); } } int main() { cin >> n >> m; cin >> p1.i >> p1.j >> p1.k >> p2.i >> p2.j >> p2.k; for(int i = 1 ; i <= m ; i++) { int x , y , z; cin >> x >> y >> z; a[x][y][z] = -1; } lee(p1); cout << a[p2.i][p2.j][p2.k] << '\n'; int l = 1; dr[1] = p2; int i , j , k; i = p2.i , j = p2.j , k = p2.k; while(i != p1.i || j != p1.j || k != p1.k) { for(int d = 0 ; d < 6 ; d++) { int inou = i + di[d]; int jnou = j + dj[d]; int knou = k + dk[d]; if(a[inou][jnou][knou] == a[i][j][k] - 1) { l++; dr[l].i = inou; dr[l].j = jnou; dr[l].k = knou; i = inou; j = jnou; k = knou; break; } } } for(int i = l ; i >= 1 ; i--) { cout << dr[i].i << " " << dr[i].j << " " << dr[i].k << '\n'; } }