OpenJudge/Poj 1191 棋盘分割

1.链接地址:

http://bailian.openjudge.cn/practice/1191/

http://poj.org/problem?id=1191

2.题目:

总时间限制:
1000ms
内存限制:
65536kB
描述
将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘。(每次切割都只能沿着棋盘格子的边进行)
OpenJudge/Poj 1191 棋盘分割

原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和。现在需要把棋盘按上述规则分割成n块矩形棋盘,并使各矩形棋盘总分的均方差最小。
均方差 ,其中平均值 ,xi为第i块矩形棋盘的总分。
请编程对给出的棋盘及n,求出O'的最小值。
输入
第1行为一个整数n(1 < n < 15)。
第2行至第9行每行为8个小于100的非负整数,表示棋盘上相应格子的分值。每行相邻两数之间用一个空格分隔。
输出
仅一个数,为O'(四舍五入精确到小数点后三位)。
样例输入
3

1 1 1 1 1 1 1 3

1 1 1 1 1 1 1 1

1 1 1 1 1 1 1 1

1 1 1 1 1 1 1 1

1 1 1 1 1 1 1 1

1 1 1 1 1 1 1 1

1 1 1 1 1 1 1 0

1 1 1 1 1 1 0 3
样例输出
1.633
来源
Noi 99

3.思路:

确定公式的常量

深搜+剪枝

4.代码:

  1 #include <iostream>

  2 #include <cstdio>

  3 #include <cmath>

  4 

  5 #define NUM 8

  6 

  7 using namespace std;

  8 

  9 double res_sigma;

 10 

 11 int n;

 12 int arr[NUM][NUM];

 13 

 14 double all_avg;

 15 

 16 double sigma;

 17 

 18 void dfs(int x1,int y1,int x2,int y2,int sum,int cut)

 19 {

 20     int k,i,j;

 21     int temp_sum,temp_avg;

 22     double temp;

 23 

 24     if(cut == 0)

 25     {

 26         temp = (sum - all_avg) * (sum - all_avg);

 27         if(sigma + temp < res_sigma) {res_sigma = sigma + temp;}

 28         return;

 29     }

 30 

 31     temp_sum = 0;

 32     for(k = y1; k < y2; ++k)

 33     {

 34         for(j = x1; j <= x2; ++j) temp_sum += arr[k][j];

 35 

 36         temp_avg = temp_sum;

 37         temp = (all_avg - temp_avg) * (all_avg - temp_avg);

 38         if(sigma + temp < res_sigma) 

 39         {

 40             sigma += temp;

 41             dfs(x1,k + 1,x2,y2,sum - temp_sum,cut - 1);

 42             sigma -= temp;

 43         }

 44 

 45         temp_avg = sum - temp_sum;

 46         temp = (all_avg - temp_avg) * (all_avg - temp_avg);

 47         if(sigma + temp < res_sigma)

 48         {

 49             sigma += temp;

 50             dfs(x1,y1,x2,k,temp_sum,cut - 1);

 51             sigma -= temp;

 52         }

 53         

 54     }

 55 

 56     temp_sum = 0;

 57     for(k = x1; k < x2; ++k)

 58     {

 59         for(i = y1; i <= y2; ++i) temp_sum += arr[i][k];

 60 

 61         temp_avg = temp_sum;

 62         temp = (all_avg - temp_avg) * (all_avg - temp_avg);

 63         if(sigma + temp < res_sigma) 

 64         {

 65             sigma += temp;

 66             dfs(k + 1,y1,x2,y2,sum - temp_sum,cut - 1);

 67             sigma -= temp;

 68         }

 69 

 70         temp_avg = sum - temp_sum;

 71         temp = (temp_avg - all_avg) * (temp_avg - all_avg);

 72         if(sigma + temp < res_sigma)

 73         {

 74             sigma += temp;

 75             dfs(x1,y1,k,y2,temp_sum,cut - 1);

 76             sigma -= temp;

 77         }

 78         

 79     }

 80 }

 81 

 82 int main()

 83 {

 84     //freopen("C://input.txt","r",stdin);

 85 

 86     cin >> n;

 87 

 88 

 89     int i,j;

 90 

 91     int sum = 0;

 92     for(i = 0; i < NUM; ++i)

 93     {

 94         for(j = 0; j < NUM; ++j)

 95         {

 96             cin >> arr[i][j];

 97             sum += arr[i][j];

 98         }

 99     }

100     all_avg = sum * 1.0 / n;

101 

102     res_sigma = sum * sum * n;

103 

104     dfs(0,0,NUM - 1,NUM - 1,sum,n - 1);

105 

106     cout.setf(ios::fixed);

107     cout.precision(3);

108     cout << sqrt(res_sigma / n) << endl;

109 

110     return 0;

111 }

 

你可能感兴趣的:(open)