解题报告 转化模式

四:zj之转化模式 众所舟舟知……zj同学会转换模式,我们对两种模式的定义为;♀♂,其实zj的模式转换是建立在他身体的细胞模式转换之上的,比如说这里有6*6的细胞: ♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

所以大家就知道为什么zj的模式总是介于两者之间了,因为他的每个细胞的模式不一样! Zj的细胞和zj一样有很多的坏毛病,当一个细胞转换模式时,他也会使它上,下,左,右四个细胞转换模式,但是仍算转换一步。比如,对于上图(1,2)的转换模式后总的模式变为:

♂♀♂♂♀♂

♀♀♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

(3,3)转换模式后总的模式变为:

♀♂♀♂♀♂

♀♂♂♂♀♂

♀♀♂♀♀♂

♀♂♂♂♀♂

♀♂♀♂♀♂

♀♂♀♂♀♂

好了,现在问题来了,zj现在想把n*n的细胞全部转换成♂模式,若不能转化输出‘NO’,若能输出最少需要几步。

注意:为了描述生动应用了♀♂符号,但word中的符号与pascal中的不一样,读入以pascal中的为准,pascal中为了转换方便最好使用ASCII码,♂11,♀12.

样例输入:(数据请粘贴change.in)(粘到pascal中就能看到了)

3

♂♀♂

♀♀♀

♂♀♂

样例输出:

1

范围: 50% n<=5; 100% n<=10;

枚举+模拟 (规定 ♂ 为 1,♀ 为 0) 首先, dfs 第一行, dfs 它是变还是不变。然后从第二行开始模拟,如果第一行对应的变了,那么他一定变,以此类推。如果第一行不是 1 ,那么为了让第一行全变成 1 ,则,它一定要变,然后在模拟第三行。。。。。。 最后判断最后一行是否全是 1 ,如果全是 1 ,则成功,反之,输出 NO 或继续 DFS 第一行。

代码(XMC)

var i,j,k,n,m,p,ii,jj:Longint;

a,b:array[1..11,1..11] of integer;

ch:char; sum,ans:longint;

flag:boolean;

procedure init;

begin

readln(n);

for i:=1 to n do

begin

for j:=1 to n do

begin

read(ch);

if ord(ch)=11 then a[i,j]:=1 else a[i,j]:=0;

end;

readln;

end;

end;

procedure main;

begin

ans:=maxlongint;

for i:=0 to (1<<n-1) do

begin

sum:=0;

b:=a;

for j:=1 to n do

if (i and (1<<(n-j)))<>0 then

begin

inc(sum);

b[1,j]:=1-b[1,j];

b[2,j]:=1-b[2,j];

if (j<>1) then b[1,j-1]:=1-b[1,j-1];

if (j<>n) then b[1,j+1]:=1-b[1,j+1];

end;

for ii:=2 to n do

for jj:=1 to n do

begin

if b[ii-1,jj]=0 then

begin

inc(sum);

b[ii,jj]:=1-b[ii,jj];

if (ii<>n) then b[ii+1,jj]:=1-b[ii+1,jj];

if (jj<>1) then b[ii,jj-1]:=1-b[ii,jj-1];

if (jj<>n) then b[ii,jj+1]:=1-b[ii,jj+1];

end;

end;

flag:=true;

for ii:=1 to n do

if b[n,ii]=0 then flag:=false;

if flag and (sum<ans) then ans:=sum;

end;

if ans=maxlongint then writeln('NO') else writeln(ans);

end;

begin

assign(input,'change.in');reset(input);

assign(output,'change.out');rewrite(output);

init;

main;

close(input); close(output);

end.

posted @ 2011-10-19 19:42  木小漾  阅读(296)  评论(0编辑  收藏  举报