Gym - 100625F Count Ways 快速幂+容斥原理

题意:n*m的格子,中间有若干点不能走,问从左上角到右下角有多少种走法。

思路:CountWay(i,j) 表示从 i 点到 j 点的种数。然后用容斥原理加加减减解决

 1 #pragma comment(linker, "/STACK:1000000000")
 2 #include <iostream>
 3 #include <cstdio>
 4 #include <fstream>
 5 #include <algorithm>
 6 #include <cmath>
 7 #include <deque>
 8 #include <vector>
 9 #include <queue>
10 #include <string>
11 #include <cstring>
12 #include <map>
13 #include <stack>
14 #include <set>
15 #define LL long long
16 #define MAXN 100005
17 #define MOD 1000000007
18 #define INF 0x3f3f3f3f
19 #define eps 1e-8
20 using namespace std;
21 struct Node
22 {
23     LL x, y;
24 };
25 Node p[MAXN];
26 LL factor[2 * MAXN], w[2 * MAXN];
27 LL res[MAXN];
28 bool compare(Node a, Node b)
29 {
30     return a.x < b.x || (a.x == b.x && a.y < b.y);
31 }
32 LL CountWay(LL x, LL y)
33 {
34     LL res = factor[x + y];
35     res = res * w[x] % MOD;
36     res = res * w[y] % MOD;
37     return res;
38 }
39 LL quick_power(LL x, LL y)
40 {
41     if (y == 0){
42         return (LL)1;
43     }
44     if (y == 1){
45         return x % MOD;
46     }
47     LL res = quick_power(x, y >> 1);
48     res = (res * res) % MOD;
49     if (y & 1){
50         res = (res * x) % MOD;
51     }
52     return res;
53 }
54 int main()
55 {
56 #ifndef ONLINE_JUDGE
57     freopen("in.txt", "r", stdin);
58     //freopen("out.txt", "w", stdout);
59 #endif // OPEN_FILE
60     int T;
61     factor[0] = 1;
62     w[0] = 1;
63     for (LL i = 1; i <= 200000; i++){
64         factor[i] = (factor[i - 1] * i) % MOD;
65         w[i] = quick_power(factor[i], MOD - 2);
66     }
67     scanf("%d", &T);
68     LL n, m, k;
69     while (T--){
70         scanf("%I64d%I64d%I64d", &n, &m, &k);
71         for (int i = 1; i <= k; i++){
72             scanf("%I64d%I64d", &p[i].x, &p[i].y);
73         }
74         p[k + 1].x = n;
75         p[k + 1].y = m;
76         sort(p + 1, p + k + 1, compare);
77         for (int i = 1; i <= k + 1; i++){
78             res[i] = CountWay(p[i].x - 1, p[i].y - 1);
79         }
80         for (int i = 1; i <= k + 1; i++){
81             for (int j = i + 1; j <= k + 1; j++){
82                 if (p[j].x < p[i].x || p[j].y < p[i].y) continue;
83                 //if(p[j].x == p[i].x && p[j].y == p[i].y) continue;
84                 res[j] = (res[j] - (res[i] * CountWay(p[j].x - p[i].x, p[j].y - p[i].y)) % MOD) % MOD;
85             }
86         }
87         printf("%I64d\n", (res[k + 1] + MOD) % MOD);
88     }
89 }
时间: 2024-10-11 21:01:26

Gym - 100625F Count Ways 快速幂+容斥原理的相关文章

CodeForces Gym 100935D Enormous Carpet 快速幂取模

Enormous Carpet Time Limit:2000MS     Memory Limit:65536KB     64bit IO Format:%I64d & %I64u Gym 100935D Description standard input/outputStatements Ameer is an upcoming and pretty talented problem solver who loves to solve problems using computers.

2017中国大学生程序设计竞赛 - 网络选拔赛 HDU 6155 Subsequence Count 矩阵快速幂

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6155 题意: 题解来自:http://www.cnblogs.com/iRedBean/p/7398272.html 先考虑dp求01串的不同子序列的个数. dp[i][j]表示用前i个字符组成的以j为结尾的01串个数. 如果第i个字符为0,则dp[i][0] = dp[i-1][1] + dp[i-1][0] + 1,dp[i][1] = dp[i-1][1] 如果第i个字符为1,则dp[i][1

hdu6470 Count 矩阵快速幂

hdu6470 1 #include <bits/stdc++.h> 2 using namespace std; 3 typedef long long ll; 4 const int maxn = 6, mod = 123456789; 5 6 struct MAT { 7 ll a[maxn][maxn]; 8 MAT(){ memset(a,0,sizeof(a)); } 9 MAT operator*(MAT p) { 10 MAT res; 11 for (int i = 0; i

UVALive 7040 Color (容斥原理+逆元+组合数+费马小定理+快速幂)

题目:传送门. 题意:t组数据,每组给定n,m,k.有n个格子,m种颜色,要求把每个格子涂上颜色且正好适用k种颜色且相邻的格子颜色不同,求一共有多少种方案,结果对1e9+7取余. 题解: 首先可以将m 与后面的讨论分离.从m 种颜色中取出k 种颜色涂色,取色部分有C(m, k) 种情况: 然后通过尝试可以发现,第一个有k种选择,第二个因不能与第一个相同,只有(k-1) 种选择,第三个也只需与第二个不同,也有(k-1) 种选择.总的情况数为k ×(k-1)^(n-1).但这仅保证了相邻颜色不同,总

HDU2157 How many ways??---(邻接矩阵,图论,矩阵快速幂)

http://acm.hdu.edu.cn/showproblem.php?pid=2157 How many ways?? Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 3013    Accepted Submission(s): 1154 Problem Description 春天到了, HDU校园里开满了花, 姹紫嫣红, 非常

HDU 2157 How many ways??(矩阵快速幂)

How many ways?? Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Submission(s): 1912    Accepted Submission(s): 692 Problem Description 春天到了, HDU校园里开满了花, 姹紫嫣红, 非常美丽. 葱头是个爱花的人, 看着校花校草竞相开放, 漫步校园, 心情也变得舒畅. 为了多看看这迷

HDOJ How many ways?? 2157【矩阵快速幂】

How many ways?? Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 2046    Accepted Submission(s): 758 Problem Description 春天到了, HDU校园里开满了花, 姹紫嫣红, 非常美丽. 葱头是个爱花的人, 看着校花校草竞相开放, 漫步校园, 心情也变得舒畅. 为了多看看这

K. Random Numbers(Gym 101466K + 线段树 + dfs序 + 快速幂 + 唯一分解)

题目链接:http://codeforces.com/gym/101466/problem/K 题目: 题意: 给你一棵有n个节点的树,根节点始终为0,有两种操作: 1.RAND:查询以u为根节点的子树上的所有节点的权值的乘积x,及x的因数个数. 2.SEED:将节点u的权值乘以x. 思路: 比赛时少看了因数不大于13这句话,然后本题难度增加数倍,肝了两个小时都没肝出来,对不起队友啊,今天的组队训练赛实力背锅…… 这题一眼线段树,由于是对一棵子树进行处理,因此我们采用常规套路,借助dfs序将子树

Count Numbers(矩阵快速幂)

Count Numbers 时间限制: 8 Sec  内存限制: 128 MB提交: 43  解决: 19[提交] [状态] [讨论版] [命题人:admin] 题目描述 Now Alice wants to sum up all integers whose digit sum is exactly ab .However we all know the number of this kind of integers are unlimited. So she decides to sum u