棋盘分割

【题目描述】
 将一个8×8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部 分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩 下的矩形棋盘共有 n 块矩形棋盘。(每次切割都只能沿着棋盘格子的边进行)

原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和。现在需要把棋盘按上述规则分割成n块矩形棋盘,并使各矩形棋盘总分的均方差最小。
请编程对给出的棋盘及 n,求出方差的最小值。

【输入描述】
第 1 行为一个整数 n(1<n<15)。
第 2 行至第 9 行每行为 8 个小于 100 的非负整数,表示棋盘上相应格子的分 值。每行相邻两数之间用一个空格分隔。

【输出描述】
仅一个数,为方差(四舍五入精确到小数点后三位)。

【样例输入】
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

源代码:

#include<cmath>
#include<iostream>
#include<iomanip> //包含【setprecision()】、【fixed】,用于四舍五入保留小数。
#define INF 1000000000 //定义极大值。
using namespace std;
double n,num(0),ans,i[9][9]={0},sum[9][9]={0},f[16][9][9][9][9]; //皆为double类型,方便下面的计算。
int main()
{
    cin>>n; //cin输入流。
    int m=n; //作为int类型数组标志变量。
    for (int a=1;a<=8;a++)
      for (int b=1;b<=8;b++)
      {
        cin>>i[a][b];
          num+=i[a][b]; //总和。
          sum[a][b]=sum[a][b-1]+sum[a-1][b]-sum[a-1][b-1]+i[a][b]; //计算[1][1][a][b]的矩形区间和。
      }
    for (int a=1;a<=8;a++)
      for (int b=1;b<=8;b++)
        for (int c=a;c<=8;c++)
          for (int d=b;d<=8;d++)
          {
              double t;
            t=sum[c][d]-sum[c][b-1]-sum[a-1][d]+sum[a-1][b-1];
            f[0][a][b][c][d]=t*t; //初始化f[切数][x1][y1][x2][y2]数组。
          }
    for (int k=1;k<n;k++) //切了多少次。
      for (int a=1;a<=8;a++)
        for (int b=1;b<=8;b++)
          for (int c=a;c<=8;c++)
            for (int d=b;d<=8;d++)
            {
                f[k][a][b][c][d]=INF; //初始化。
                for (int t=a;t<c;t++) //横切。
                {
                    f[k][a][b][c][d]=min(f[k][a][b][c][d],f[0][a][b][t][d]+f[k-1][t+1][b][c][d]);
                    f[k][a][b][c][d]=min(f[k][a][b][c][d],f[0][t+1][b][c][d]+f[k-1][a][b][t][d]);
                }
                for (int t=b;t<d;t++) //纵切。
                {
                    f[k][a][b][c][d]=min(f[k][a][b][c][d],f[0][a][b][c][t]+f[k-1][a][t+1][c][d]);
                    f[k][a][b][c][d]=min(f[k][a][b][c][d],f[0][a][t+1][c][d]+f[k-1][a][b][c][t]);
                }
            }
    ans=f[m-1][1][1][8][8]/n-(num/n)*(num/n); //切的次数=矩形个数-1。
    cout<<setprecision(3)<<fixed<<sqrt(ans); //亟待学习。
    return 0;
}
时间: 2024-11-01 11:04:27

棋盘分割的相关文章

POJ1191——棋盘分割

棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 12456   Accepted: 4389 Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行) 原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规

POJ 1191 棋盘分割

棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 11938   Accepted: 4207 Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行) 原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规

递归,记忆化搜索,(棋盘分割)

题目链接http://poj.org/problem?id=1191 Problem: 1191User: yinjianMemory: 568KTime: 16MSLanguage: C++Result: Accepted 解题报告: 1.公式可以利用数学方法化简,就是求各个矩阵上的数(的和)的平方和最小. 2.每一次分割都有四种情况(递归). 3.每一次分割的位置要进行比较,从而找到最佳. #include <stdio.h> #include <math.h> #includ

【POJ 1191】 棋盘分割(DP)

[POJ 1191] 棋盘分割(DP) Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 13811   Accepted: 4917 Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行) 原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分

棋盘分割(记忆化搜索)

棋盘分割 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 501    Accepted Submission(s): 248 Problem Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.

NOI 193棋盘分割.cpp

193:棋盘分割 查看 提交 统计 提问 总时间限制:  1000ms 内存限制:  65536kB 描述 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行)原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规则分割成n块矩形棋盘,并使各矩形棋盘总分的均方差最小.均方差,其中平均值,xi为第i块矩形棋盘的

POJ1991 NOI1999棋盘分割

棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 15581   Accepted: 5534 Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行) 原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规

poj1191 棋盘分割【区间DP】【记忆化搜索】

棋盘分割 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 16263   Accepted: 5812 Description 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行) 原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规

POJ百炼——1191棋盘分割

1191:棋盘分割 总时间限制: 1000ms 内存限制: 65536kB 描述 将一个8*8的棋盘进行如下分割:将原棋盘割下一块矩形棋盘并使剩下部分也是矩形,再将剩下的部分继续如此分割,这样割了(n-1)次后,连同最后剩下的矩形棋盘共有n块矩形棋盘.(每次切割都只能沿着棋盘格子的边进行)原棋盘上每一格有一个分值,一块矩形棋盘的总分为其所含各格分值之和.现在需要把棋盘按上述规则分割成n块矩形棋盘,并使各矩形棋盘总分的均方差最小.均方差,其中平均值,xi为第i块矩形棋盘的总分.请编程对给出的棋盘及

poj - 1191 - 棋盘分割(dp)

题意:将一个8*8的棋盘(每个单元正方形有个分值)沿直线(竖或横)割掉一块,留下一块,对留下的这块继续这样操作,总共进行n - 1次,得到n块(1 < n < 15)矩形,每个矩形的分值就是单元正方形的分值的和,问这n个矩形的最小均方差. 题目链接:http://poj.org/problem?id=1191 -->>此题中,均方差比较,等价于方差比较,等价于平方和比较.. 状态:dp[x1][y1][x2][y2][i]表示将(x1, y1)到(x2, y2)的矩形分割i次的最小