cf232 B. Table(dp)

题意:

在 n×m 网格中安排点,要求任意 n×n 矩阵中恰有 k 个点。求方案数。

n100nm1e18,0kn2

思路:

观察发现第 i 列和第 i+n 列的点数须相等。下面的列 i 均指所有模 n 余 i 的列。

f[i][j] 表示在第 1i 列中选 j 个的方案数,j[0,k]。 枚举第 i 列放 t 个,t[0,min{n,k}]

f[i][j]=t=0min{n,j}f[i1][jt]×(Cnt)cnti

答案是 f[n][k]

const int N = 110;
const ll MOD = 1e9 + 7;

ll n, m, k, C[N][N], po[N][N], f[N][N*N];

ll qmi(ll a, ll b, ll p = MOD)
{
    ll res = 1;
    while(b) {
        if(b & 1) res = res * a % p;
        a = a * a % p, b >>= 1;
    }
    return res;
}

ll cnt(ll i)
{
    return i <= m%n ? m/n + 1 : m/n;
}

signed main()
{
    cin >> n >> m >> k;
    
    for(int i = 0; i <= n; i++) //预处理组合数
    {
        C[i][0] = 1;
        for(int j = 1; j <= i; j++)
            C[i][j] = (C[i-1][j-1] + C[i-1][j]) % MOD;
    }

    for(int i = 0; i <= n; i++) //预处理幂
        for(int j = 1; j <= n; j++)
            po[i][j] = qmi(C[n][i], cnt(j));

    f[0][0] = 1;
    for(ll i = 1; i <= n; i++)
        for(ll j = 0; j <= k; j++)
            for(ll t = 0; t <= min(n, j); t++)
                (f[i][j] += f[i-1][j-t] * po[t][i] % MOD) %= MOD;

    cout << f[n][k];

}

posted @   Bellala  阅读(38)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 展开说说关于C#中ORM框架的用法!
点击右上角即可分享
微信分享提示