Hướng dẫn giải của VM 08 Bài 20 - Mê cung
Chỉ dùng lời giải này khi không có ý tưởng, và đừng copy-paste code từ lời giải này. Hãy tôn trọng người ra đề và người viết lời giải.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Nộp một lời giải chính thức trước khi tự giải là một hành động có thể bị ban.
Lưu ý: Các code mẫu dưới đây chỉ mang tính tham khảo và có thể không AC được bài tập này
Code mẫu của flashmt
const fi=''; fo=''; maxn=210; oo=1000000000; var n,m,s,sum:longint; a,b:array[1..maxn,1..maxn] of longint; re,f:array[1..maxn*maxn] of longint; procedure rf; var i,x,y:longint; begin read(n,m); for x:=1 to n do for y:=1 to n do a[x,y]:=-oo; for i:=1 to m do begin read(x,y,a[x,y]); a[y,x]:=a[x,y]; sum:=sum+a[x,y]; end; b:=a; end; procedure work; var i,pos,min:longint; begin min:=oo+oo; for i:=2 to m+1 do begin f[i]:=f[i-1]+b[re[i],re[i-1]]; if f[i]<min then begin min:=f[i]; pos:=i; end; end; if pos=m+1 then pos:=1; for i:=pos to m do write(re[i],' '); for i:=1 to pos do write(re[i],' '); end; procedure try(i,x:longint); var y,t:longint; begin if (i>m+1) and (re[m+1]=re[1]) then begin work; close(input); close(output); halt; end; for y:=1 to n do if a[x,y]<>-oo then begin re[i]:=y; t:=a[x,y]; a[x,y]:=-oo; a[y,x]:=-oo; try(i+1,y); a[y,x]:=t; a[x,y]:=t; end; end; procedure pr; var i:longint; begin if sum<0 then writeln(-1) else begin re[1]:=1; try(2,1); writeln(-1); end; end; begin assign(input,fi); reset(input); assign(output,fo); rewrite(output); rf; pr; close(input); close(output); end.
Code mẫu của ladpro98
#include <bits/stdc++.h> const int N = 201; const int oo = 1000000000; using namespace std; int a[N][N], n, m, d, res[N*N], Q[N*N], F[N*N], deg[N]; bool Link[N][N]; bool ok(int pos) { if (d != m+1) return false; for(int i=1; i<=n; i++) if (deg[i] & 1) return false; int sum = 0; for(int i=pos; i<d; i++) { sum += a[res[i]][res[i+1]]; if (sum < 0) return false; } for(int i=1; i<pos; i++) { sum += a[res[i]][res[i+1]]; if (sum < 0) return false; } return true; } int main() { //freopen("PCYCLE.in", "r", stdin); scanf("%d %d\n", &n, &m); int i, u, v, c; for(i=1; i<=m; i++) { scanf("%d %d %d\n", &u, &v, &c); Link[u][v] = true; Link[v][u] = true; a[u][v] = c; a[v][u] = c; deg[u]++; deg[v]++; } int top = 1; Q[1] = 1; while (top) { u = Q[top]; for(v=1; v<=n; v++) { if (Link[u][v]) { Link[u][v] = false; Link[v][u] = false; top++;Q[top] = v; break; } } if (u == Q[top]) { d++;res[d] = u; top--; } } //for(i=1; i<=d; i++) printf("%d ", res[i]); int low = oo, start; F[1] = 0; for(i=2; i<=d; i++) { F[i] = F[i-1] + a[res[i]][res[i-1]]; if (F[i] < low) { low = F[i]; start = i; } } if (!ok(start)) printf("-1"); else { for(i=start; i<=d; i++) printf("%d ", res[i]); for(i=2; i<=start; i++) printf("%d ", res[i]); } return 0; }
Code mẫu của RR
{$R+,Q+} PROGRAM PCYCLE; CONST FINP=''; FOUT=''; maxn=202; maxm=20002; VAR c:array[0..maxn,0..maxn] of longint; x:array[1..maxn,1..maxn] of longint; total:array[1..maxm+1] of longint; deg,xet:array[1..maxn] of longint; e,s:array[1..maxm+1] of longint; start,n,m:longint; procedure readInput; var f:text; i,u,v:longint; begin assign(f,FINP); reset(f); read(f,n,m); for i:=1 to m do begin read(f,u,v,c[u,v]); c[v,u]:=c[u,v]; x[u,v]:=1; x[v,u]:=1; inc(deg[u]); inc(deg[v]); end; close(f); end; function ktlt:boolean; var i:longint; procedure DFS(u:longint); var v:longint; begin xet[u]:=1; for v:=1 to n do if (x[u,v]=1) and (xet[v]=0) then DFS(v); end; begin DFS(1); ktlt:=false; for i:=1 to n do if xet[i]=0 then exit; ktlt:=true; end; function ktctE:boolean; var i:longint; begin ktctE:=false; for i:=1 to n do if deg[i] mod 2<>0 then exit; ktctE:=true; end; procedure writeOutput(k:longint); var f:text; i,j:longint; begin assign(f,FOUT); rewrite(f); if k=0 then begin writeln(f,-1); close(f); halt; end; j:=start; for i:=1 to m+1 do begin write(f,e[j],' '); inc(j); if j=m+1 then j:=1; end; close(f); end; procedure EulerCycle; var top,u,i,sl:longint; begin top:=1; s[1]:=n; sl:=0; while top>0 do begin u:=s[top]; i:=1; while (i<=n) and (x[u,i]=0) do inc(i); if i<=n then begin inc(top); s[top]:=i; x[u,i]:=0; x[i,u]:=0; end else begin inc(sl); e[sl]:=u; dec(top); end; end; end; procedure process; var i:longint; begin for i:=2 to m+1 do total[i]:=total[i-1]+c[e[i-1],e[i]]; start:=1; for i:=2 to m+1 do if total[i]<total[start] then start:=i; if start=m+1 then start:=1; end; function ktok:boolean; var i,j:longint; t:longint; begin ktok:=false; t:=0; j:=start; for i:=1 to m+1 do begin t:=t+c[e[j],e[j+1]]; if t<0 then exit; inc(j); if j=m+1 then j:=1; end; ktok:=true; end; BEGIN readInput; if not ktlt then writeOutput(0); if not ktctE then writeOutput(0); EulerCycle; process; if not ktok then writeOutput(0); writeOutput(1); END.
Bình luận