• POJ1958:Strange Towers of Hanoi


    我对状态空间的理解:https://www.cnblogs.com/AKMer/p/9622590.html

    题目传送门:http://poj.org/problem?id=1958

    题目要我们求四柱汉诺塔的步数最小值,将盘子数在(1)(12)之间的全部求出来。

    状态空间即为移动盘子对应的步数。

    对于三柱汉诺塔,相信大家都非常熟悉了。我们假设三柱汉诺塔上有(n)个盘子,(f[n])表示将(n)个盘子移动到另一根柱子上的最小步数,那么显然:

    (f[n]=f[n-1]*2+1)

    就相当于你先把上面(n-1)个盘子先移到第二跟柱子上,然后用一步把最后的大盘子移动到第三根柱子上。再把那(n-1)个盘子移到第三根柱子上。

    那么在题目要求的四柱条件下,状态就可以用三柱条件下的状态扩展得来。设(g[n])表示四柱条件下(n)个盘子从第一根全部移到另一根的最小步数。

    那么显然:

    (g[n]=min){(sum_{i=1}^{n-1}g[i]*2+g[n-i])}

    就是枚举先将(i)个盘子移动到另一根柱子上,然后将剩下的盘子在三柱条件下移动到最后一根柱子上,再将先前的(i)根柱子移动到最后一根柱子上去。

    时间复杂度:(O(n^2))

    空间复杂度:(O(n))

    代码如下:

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    
    int n=12;
    int f[13],g[13];
    
    int read() {
    	int x=0,f=1;char ch=getchar();
    	for(;ch<'0'||ch>'9';ch=getchar())if(ch=='-')f=-1;
    	for(;ch>='0'&&ch<='9';ch=getchar())x=x*10+ch-'0';
    	return x*f;
    }
    
    int main() {
    	memset(g,63,sizeof(g));
    	g[1]=1;
    	for(int i=1;i<=n;i++)
    		f[i]=f[i-1]*2+1;
    	for(int i=2;i<=n;i++)
    		for(int j=1;j<i;j++)
    			g[i]=min(g[i],g[j]*2+f[i-j]);
    	for(int i=1;i<=n;i++)
    		printf("%d
    ",g[i]);
    	return 0;
    }
    
  • 相关阅读:
    《秋日》 -- 程颢
    《安乐吟》 -- 邵雍
    《大学》笔记
    《跨越鸿沟》笔记
    庄子《齐物论》—— 方生方死、因是因非是对立统一规律的起源
    《饮酒(其五)》陶渊明
    《亲密关系》笔记
    《人生的智慧》笔记
    《历史的教训》笔记
    《格鲁夫给经理人的第一课》笔记
  • 原文地址:https://www.cnblogs.com/AKMer/p/9625746.html
Copyright © 2020-2023  润新知