• 【Cf #178 A】Shaass and Lights(组合数)


    考虑两个灯之间的暗灯,能从左边或右边点亮两种顺序,而最左端或最右端只有一种点亮顺序。

    先不考虑点灯顺序,总共有n - m个灯要点亮,对于连续的一段暗灯,他们在总的点灯顺序中的是等价的,于是问题就可以抽象成有重复元素的组合数:

    $ C = frac{ (n - m)! }{ prod_{i = 1}^{k} \, x_{i} ! }  $ 。

    在考虑一段连续的暗灯内部的点灯顺序,只要让答案乘上 $ 2 ^ {len - 1} $ 即可。

    $ igodot $ 技巧&套路:

    • 组合数应用的模型,组合数的运用
     1 #include <cstdio>
     2 #include <algorithm>
     3 
     4 typedef long long LL;
     5 const int N = 1005, MOD = 1e9 + 7;
     6 
     7 int n, m, a[N], d[N], pw2[N], fac[N];
     8 
     9 int Pow(int x, int b, int re = 1) {
    10     for (; b; b >>= 1, x = (LL) x * x % MOD) if (b & 1) re = (LL) re * x % MOD;
    11     return re;
    12 }
    13 
    14 int main() {
    15     scanf("%d%d", &n, &m);
    16     pw2[0] = fac[0] = 1;
    17     for (int i = 1; i <= m; ++i) {
    18         scanf("%d", &a[i]);
    19     }
    20     for (int i = 1; i <= n; ++i) {
    21         pw2[i] = pw2[i - 1] * 2 % MOD;
    22         fac[i] = (LL) fac[i - 1] * i % MOD;
    23     }
    24     std::sort(a + 1, a + 1 + m);
    25     
    26     int ans = fac[n - m];
    27     for (int i = 1; i < m; ++i) {
    28         int d = a[i + 1] - a[i] - 1;
    29         if (d == 0) continue;
    30         ans = (LL) ans * Pow(fac[d], MOD - 2) % MOD;
    31         ans = (LL) ans * pw2[d - 1] % MOD;
    32     }
    33     if (a[1] > 1) ans = (LL) ans * Pow(fac[a[1] - 1], MOD - 2) % MOD;
    34     if (a[m] < n) ans = (LL) ans * Pow(fac[n - a[m]], MOD - 2) % MOD;
    35     printf("%d
    ", ans);
    36     
    37     return 0;
    38 }
    View Code
  • 相关阅读:
    一个类GraphQL的ORM数据访问框架发布
    关于 IIS Express 常用设置
    代码失控与状态机(上)
    实体类的动态生成(三)
    实体类的动态生成(二)
    搭建 github.io 博客站点
    实体类的动态生成(一)
    JDK的下载和安装
    三步搞定jupyter nootebook 主题切换
    LeetCode刷题--存在重复元素
  • 原文地址:https://www.cnblogs.com/Dance-Of-Faith/p/9296652.html
Copyright © 2020-2023  润新知