POJ 1191 棋盘分割(DP)

题目链接

大体思路看,黑书。。。其他就是注意搞一个in数组,这样记忆化搜索,貌似比较快。

 1 #include <cstdio>

 2 #include <cstring>

 3 #include <iostream>

 4 #include <cmath>

 5 using namespace std;

 6 #define INF 0x7fffffff

 7 int p[10][10],sum[10][10];

 8 double dp[11][11][11][11][21];

 9 int in[11][11][11][11][21];

10 double s[11][11][11][11];

11 int dfs(int x1,int y1,int x2,int y2,int k)

12 {

13     int i;

14     if(in[x1][y1][x2][y2][k])

15     return dp[x1][y1][x2][y2][k];

16     if(k == 1)

17     {

18         in[x1][y1][x2][y2][k] = 1;

19         return dp[x1][y1][x2][y2][k] = s[x1][y1][x2][y2];

20     }

21     else

22     {

23         double minz = INF;

24         for(i = x1;i < x2;i ++)

25         {

26             minz = min(dfs(x1,y1,i,y2,k-1)+s[i+1][y1][x2][y2],minz);

27             minz = min(dfs(i+1,y1,x2,y2,k-1)+s[x1][y1][i][y2],minz);

28         }

29         for(i = y1;i < y2;i ++)

30         {

31             minz = min(dfs(x1,y1,x2,i,k-1)+s[x1][i+1][x2][y2],minz);

32             minz = min(dfs(x1,i+1,x2,y2,k-1)+s[x1][y1][x2][i],minz);

33         }

34         in[x1][y1][x2][y2][k] = 1;

35         return dp[x1][y1][x2][y2][k] = minz;

36     }

37 }

38 int main()

39 {

40     int i,j,k,u,v,n,temp;

41     scanf("%d",&n);

42     temp = 0;

43     for(i = 1;i <= 8;i ++)

44     {

45         for(j = 1;j <= 8;j ++)

46         {

47             scanf("%d",&p[i][j]);

48             temp += p[i][j];

49         }

50     }

51     for(i = 1;i <= 8;i ++)

52     {

53         for(j = 1;j <= 8;j ++)

54         {

55             for(k = 1;k <= 8;k ++)

56             {

57                 for(u = 1;u <= 8;u ++)

58                 {

59                     for(v = 1;v <= n;v ++)

60                     dp[i][j][k][u][v] = INF;

61                 }

62             }

63         }

64     }

65     for(i = 1;i <= 8;i ++)

66     {

67         for(j = 1;j <= 8;j ++)

68         sum[i][j] = sum[i-1][j] + sum[i][j-1] - sum[i-1][j-1] + p[i][j];

69     }

70     for(i = 1;i <= 8;i ++)

71     {

72         for(j = 1;j <= 8;j ++)

73         {

74             for(k = 1;k <= 8;k ++)

75             {

76                 for(u = 1;u <= 8;u ++)

77                 {

78                     s[i][j][k][u] = sum[k][u]+sum[i-1][j-1]-sum[i-1][u]-sum[k][j-1];

79                     s[i][j][k][u] *= s[i][j][k][u];

80                 }

81             }

82         }

83     }

84     printf("%.3f\n",sqrt(dfs(1,1,8,8,n)*1.0/n-(temp*1.0/n)*(temp*1.0/n)));

85     return 0;

86 }

 

 

你可能感兴趣的:(poj)