汉诺塔

提交文件:hanoi.exe

输入文件:hanoi.in

输出文件:hanoi.out

题目描述

你对经典的hanoi塔问题一定已经很熟悉了。有三根柱子,n个大小不一的圆盘,要求大盘不能压在小盘上,初始时n个圆盘都在第一根柱子上,最少要多少步才能挪到最后一根柱子上?

现在我们来将hanoi塔扩展一下,由三根柱子扩展到四根柱子,其余规则不变。例如,3个圆盘,四根柱子A到D,初始时圆盘都A柱上,我们用五步就可以将圆盘都挪到D柱上:

第一步:将圆盘1从A挪到B;

第二步:将圆盘2从A挪到C;

第三步:将圆盘3从A挪到D;

第四步:将圆盘2从C挪到D;

第五步:将圆盘1从B挪到D。

你的任务是写一个程序求解四柱子hanoi塔问题最少要多少步可以解决。

输入格式(light.in):

输入只有一行,为一个正整数n。(1<=n<=1000)

输出格式(light.out):

输出为一个正整数,代表n盘四柱子hanoi塔问题最少要多少步可以解决。

样例

hanoi.in

hanoi.out

3

5

分析:

假设有n片,移动次数是f(n).显然f⑴=1,f⑵=3,f⑶=7,且f(k+1)=2*f(k)+1。此后不难证明f(n)=2^n-1。n=64时,

f(64)= 2^64-1=18446744073709551615。

代码:

var
  n:longint;


procedure init;
begin
  readln(n);
end;


procedure main;
var
  now,my2,sum:int64;
begin
  if n=1 then
    begin
      writeln(1);
      close(input);close(output);
      halt;
    end;
  if n=2 then
    begin
      writeln(3);
      close(input);close(output);
      halt;
    end;
  dec(n);
  now:=2;my2:=2;sum:=1;
  while n>now do
    begin
      dec(n,now);
      inc(sum,now*my2);
      inc(now);
      my2:=my2*2;
    end;
  inc(sum,n*my2);
  writeln(sum);
end;


begin
  assign(input,'hanoi.in');reset(input);
  assign(output,'hanoi.out');rewrite(output);
  init;
  main;
  close(input);close(output);
end.

你可能感兴趣的:(暴力)