HHKB Programming Contest 2020 D - Squares【思维】

题目链接

题目描述

在二维平面给定一个长度为n的正方形大小区域,需要将边长为a,b的正方形不相交的放入这个区域,求所有的方案数。

思路

如果两个正方形相交,即可发现其投影在x轴和y轴上的边全部重合,因此就是求边长为a,b的线段在长度为n的线段上不重合的所有摆法的方案数。而且只要这个投影在x轴上不重合或者在y轴上不重合即可。
边长为a的边左端点放在0位置上,那么b线段左端点能放的位置就是\([a, n - b]\)上的任意一点,方案数即为\(n-a-b+1\)。
同理可推出边界情况就是将线段a放在n-b-a这个位置上,b只能放在n-b这个位置上,方案数为1种。
设\(d = n - b - a\),那么所有的方案数就是\(\sum_{x = 1}^{d+1}x\),即为\((d+2)*(d+1)/2\).因为可以考虑a在b左边或者是a在b右边,就有2种方案。所以仅考虑x轴不相交的情况或者y轴不相交的情况时的方案数为\(ans1 = (d+1)*(d+2)*(n-a-1)*(n-b-1)\)。
x轴不相交y轴也不相交的情况即为\(ans2 = (d+1)^2*(d+2)^2\).
所以答案就是\(2*an1-ans2\),因为x轴y轴都不相交的计算次数多计算了一次。
注意考虑特判0的情况。

代码

#include<bits/stdc++.h>
using namespace std;

typedef long long LL;
const int mod = 1e9 + 7;

void solve() {
    LL n, a, b;
    scanf("%lld%lld%lld", &n, &a, &b);
    if(n < a + b) {
        puts("0");
        return;
    }
    LL d = n - a - b;
    LL x = d + 1, y = d + 2;
    LL res = 2 * x % mod * y % mod * (n - a + 1) % mod * (n - b + 1) % mod; res %= mod;
    res -= x * x % mod * y % mod * y % mod; res = (res + mod) % mod;
    printf("%lld\n", res);
}

int main() {
//    freopen("in.txt", "r", stdin);
    int t; scanf("%d", &t); while(t--)
    solve();
    return 0;
}

上一篇:GOGOUP-7.defer关键字


下一篇:Game Programming using Qt 5 Beginner’s Guide, 2nd Editio 学习笔记- outlinetext