这道题目自己是做过的,悲剧了,当时可能就没弄懂,或者弄懂了又忘了,刚才去核实了一下,一模一样的题目。
这说明了什么问题?
说明了不及时复习,学也是白学,说明了如果自己不是用心去对这些知识点感兴趣的话,学也是白学。说明了自己的脑子有问题,爱忘东西。
算了不埋怨自己了。
题目的描述就是2个皇后在N*M的期盼上,同一行,同一列,斜着都可以攻击对方,问你有多少种可能。
用的组合公式求解的。
首先分析,三种情况是互不干扰的,所以用加法原理:横着成立的+竖着成立的+斜着成立的。
三种情况都好分析,关键是自己没有思考。
还有一点需要特别注意,我就错了很久才发现问题,那就是保证溢出的问题。我递归的时候都没有注意到可能i会溢出所以错了,引以为戒,千万要注意溢出的问题,要不然,你可能真的会错死去。阿弥陀佛,希望自己以后一定注意。
代码很简单:
#include <stdio.h>
#include <string.h>
#include <iostream>
#include <algorithm>
#include <string>
using namespace std;
const int MAXN = 1000000 + 11;
int N, M;
long long A[MAXN];
void init()
{
A[0] = 0;
A[1] = 0;
A[2] = 0;
A[3] = 4;
for (long long i = 4; i < MAXN; i++)
{
A[i] = A[i - 1] + (i - 1) * (i - 2) * 2;
}
}
int main()
{
init();
while (scanf("%d%d", &N, &M) != EOF)
{
if (N == 0 && M == 0)
{
break;
}
if (N > M)
{
swap(N, M);
}
long long ans1 = (long long)(M - N + 1) * N * (N - 1) + A[N];
ans1 *= 2;
long long ans2 = (long long)N * M * (M - 1);
long long ans3 = (long long )N * M * (N - 1);
printf("%lld\n", ans1 + ans2 + ans3);
// printf("%lld\n", (long long) N * M * (M + N - 2) + (long long)2 * N * (N - 1) *
// ((long long)(3 * M - N - 1)) / 3);
}
// system("pause");
return 0;
}