P2241 统计方形(数据加强版)
原题描述:
题目背景
1997年普及组第一题
题目描述
有一个n*m方格的棋盘,求其方格包含多少正方形、长方形
输入格式
n,m因为原来数据太弱,现规定m小于等于5000,n小于等于5000(原来是100,100)
输出格式
方格包含多少正方形、长方形
输入输出样例
输入 #1
2 3
输出 #1
8 10
思路
一开始的想法是枚举所有正方形和长方形的形状,依次累加每种情况的值
本应该是这样的
**该代码为AC代码**
#include<iostream>
using namespace std;
long long n,m,rec,sqr;
int main() {
cin>>n>>m;
for(int i=0; i<n; i++)//循环,从0到n-1,但是计算时,数量从n-0到n-(n-1)
for(int j=0; j<m; j++) {//循环,从0到m-1,但是计算时,数量从m-0到m-(m-1)
if(i==j) sqr+=(n-i)*(m-j);//如果i==j,说明是正方形
else rec+=(n-i)*(m-j);//如果不等说明是矩形
}
cout<<sqr<<" "<<rec<<endl;//输出
return 0;
}
可以这样做是因为 矩形数量=正方形数量+长方形数量 ,而矩形总数又是(1+2+...+n) * (1+2+...+m) = (1+n)(1+m) * n * m,其实上述为了简化计算量,还可以将rec改为rec=(1+n)(1+m) * n*m-sqr
但是我傻了。。我没想到 i==j 的时候就是正方形。。然后长方形也分为左右长和上下长(看来简化思维还是任重而道远。。)
但是最后还是结合 矩形数量=正方形数量+长方形数量 这个想法AC了,关于长方形的计算,还需要进一步考虑(纳入To do list)
PS:最好用long long(虽然我也见到int也ac的代码)
个人AC代码
#include<iostream>
using namespace std;
typedef long long ll;
int main()
{
ll n,m,res=0;
cin >> n >> m;
for(ll i=1;i <= (n>m?m:n);i++) //计算正方形
{
ll row=n+1-i,col=m+1-i;
res+=row*col;
}
cout << res << " ";
ll sum=(1+n)*(1+m)*n*m/4;
cout << sum-res; //计算长方形
}