「6月雅礼集训 2017 Day2」B
【题目大意】
求n*n的棋盘,每行每列都有2个黑格子的方案数。
n<=10^7
【题解】
zzq的做法好神奇啊
行列建点,二分图
左边有i个点,右边有j个点的方案数 f[i,j]
左边有i个点,2个已经有1个度,右边有j个点的方案数 g[i,j]
g[i,j] = f[i-2,j-1]*j + g[j,i-2]*P(j,2)
f[i,j] = g[i,j-1] * C(i,2) = g[j,i-1] * C(j,2)
g[j,i-2] = g[i-1,j-1] * C(i-1,2) / C(j,2)
g[i,j] = g[i-2,j-2] * C(i-2,2) * j + g[i-1, j-1] * C(i-1,2) / C(j,2) * P(j,2)
g[i,j] = g[i-2,j-2] * C(i-2,2) * j + g[i-1, j-1] * C(i-1,2) * 2
g[x] = g[x, x-1]
g[x] = g[x-2] * C(x-2, 2) * (x-1) + g[x-1] * C(x-1, 2) * 2
ans = sigma (C(x,2) * g[x])
Q: 为什么从f转移到g,只乘了右边选择的部分,不管左边;从g转移到f,只乘了左边的部分,不管右边?
A: g实际的意义是我钦定左边最后两个度数为1的方案数,f实际的意义是我钦定右边最后1或2个是我最后填进来。 我从g到f,目的是消去两个度为1的点,重点是消去,我要优先考虑消除哪两个点,按照我g的定义,每两个度数为1的点作为选择,都有这么多方案,所以要乘组合数;从f到g,目的是制造两个度为1的点,按照f的定义,每1或2个点作为选择,都有这么多方案,所以要乘j和后面的那个组合数。意义在于,我要有一个顺序来填数,不能xjb填,这样会统计重复方案,我们用钦(ying)点来避免这样的问题。
# include <stdio.h>
# include <string.h>
# include <iostream>
# include <algorithm> using namespace std; typedef long long ll;
typedef unsigned long long ull;
typedef long double ld; # define RG register
# define ST static const int M = 1e7 + ;
const int mod = ; int n, g[M], ans; inline int C(int n, int k = ) {
return (ll)n * (n-) / % mod;
} int main() {
// freopen("B.in", "r", stdin);
// freopen("B.out", "w", stdout);
cin >> n;
g[] = , g[] = ;
for (int i=; i<=n; ++i) {
g[i] = 1ll * C(i-) * (i-) % mod * g[i-] % mod + 2ll * C(i-) * g[i-] % mod;
if(g[i] >= mod) g[i] -= mod;
}
for (int i=; i<=n; ++i) {
ans += 1ll * C(i) * g[i] % mod;
if(ans >= mod) ans -= mod;
}
cout << ans;
return ;
}
多贴几份考试写的各种暴力吧qwq
O(n^2)求单点暴力
# include <stdio.h>
# include <string.h>
# include <iostream>
# include <algorithm> using namespace std; typedef long long ll;
typedef unsigned long long ull;
typedef long double ld; # define RG register
# define ST static const int M = 1e4 + , N = 1e5 + ;
const int mod = ; int n, f[][M];
// row i, line2: j line1: k line0: l inline int C(int n, int k) {
if(k == ) return n;
if(k == ) return (ll)n * (n-) / % mod;
} int main() {
// freopen("B.in", "r", stdin);
// freopen("B.out", "w", stdout);
int pre = , cur = ; cin >> n;
for (int j=; j<=n; ++j) f[pre][j] = ;
f[pre][] = ;
for (int i=; i<=n; ++i) {
for (int j=; j<=i; ++j) {
f[cur][j] = ;
// i*2 = j*2 + k => k = i*2 - j*2
int k = i* - j*, l = n-j-k;
// printf("%d line2: %d line1: %d line0: %d\n", i, j, k, l);
if(l < ) continue;
if(j >= ) {
f[cur][j] += 1ll * C(k+, ) * f[pre][j-] % mod;
if(f[cur][j] >= mod) f[cur][j] -= mod;
}
if(k >= ) {
f[cur][j] += 1ll * C(l+, ) * f[pre][j] % mod;
if(f[cur][j] >= mod) f[cur][j] -= mod;
}
if(j && k) {
f[cur][j] += 1ll * C(k, ) * C(l+, ) * f[pre][j-] % mod; // 10w: need mod again
if(f[cur][j] >= mod) f[cur][j] -= mod;
}
// printf("F = %d\n", f[i][j]);
}
swap(pre, cur);
}
cout << f[pre][n] << ','; return ;
}
把含有n-...的项换成不含n的等价表示就有70分了。。
我是考试的时候打了个1w的表发现100K,压了一半,套这个做法。。50(被评测机卡)
「6月雅礼集训 2017 Day2」B的更多相关文章
- 「6月雅礼集训 2017 Day2」C
[题目大意] 有一棵n个点的完全二叉树,边权均为1,每个点有小鸟容量c[i] 依次来了m只小鸟,第i只小鸟初始位置在pos[i]上,问来了x只小鸟的时候,怎样安排小鸟的路线可以使得小鸟移动的边权和最小 ...
- 「6月雅礼集训 2017 Day2」A
[题目大意] 给出一棵树,求有多少对点(u,v)满足其路径上不存在两个点a,b满足(a,b)=1 n<=10^5 [题解] 考虑找出所有不符合的点对,共有n*ln(n)对,他们要么是祖先-> ...
- 「6月雅礼集训 2017 Day10」quote
[题目大意] 一个合法的引号序列是空串:如果引号序列合法,那么在两边加上同一个引号也合法:或是把两个合法的引号序列拼起来也是合法的. 求长度为$n$,字符集大小为$k$的合法引号序列的个数.多组数据. ...
- 「6月雅礼集训 2017 Day4」qyh(bzoj2687 交与并)
原题传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=2687 [题目大意] 给出若干区间,求一个区间的大于等于2的子集,使得 |区间并| 和 | ...
- 「6月雅礼集训 2017 Day11」delight
[题目大意] 有$n$天,每天能吃饭.睡觉.什么事也不干 每天吃饭的愉悦值为$e_i$,睡觉的愉悦值为$s_i$,什么都不干愉悦值为0. 要求每连续$k$天都要有至少$E$天吃饭,$S$天睡觉. 求最 ...
- 「6月雅礼集训 2017 Day11」jump
[题目大意] 有$n$个位置,每个位置有一个数$x_i$,代表从$i$经过1步可以到达的点在$[\max(1, i-x_i), \min(i+x_i, n)]$中. 定义$(i,j)$的距离表示从$i ...
- 「6月雅礼集训 2017 Day11」tree
[题目大意] 给出一棵带权树,有两类点,一类黑点,一类白点. 求切断黑点和白点间路径的最小代价. $n \leq 10^5$ [题解] 直接最小割能过..但是树形dp明显更好写 设$f_{x,0/1/ ...
- 「6月雅礼集训 2017 Day10」perm(CodeForces 698F)
[题目大意] 给出一个$n$个数的序列$\{a_n\}$,其中有些地方的数为0,要求你把这个序列填成一个1到$n$的排列,使得: $(a_i, a_j) = 1$,当且仅当$(i, j) = 1$.多 ...
- 「6月雅礼集训 2017 Day8」route
[题目大意] 给出平面上$n$个点,求一条连接$n$个点的不相交的路径,使得转换的方向符合所给长度为$n-2$的字符串. $n \leq 5000$ [题解] 考虑取凸包上一点,然后如果下一个是‘R' ...
随机推荐
- Leetcode 简略题解 - 共567题
Leetcode 简略题解 - 共567题 写在开头:我作为一个老实人,一向非常反感骗赞.收智商税两种行为.前几天看到不止两三位用户说自己辛苦写了干货,结果收藏数是点赞数的三倍有余,感觉自己的 ...
- VS2013生产过程问题及解决
TRK0002错误 现象:编译器.链接器交替报错,不能正常生成 环境:Win8.1 + VS2013 + 百度杀毒 解决:退出百度杀毒,重启VS,再进行生成 修订:发现问题依旧,经过多次试验,发现与杀 ...
- 【APUE】Chapter15 Interprocess Communication
15.1 Introduction 这部分太多概念我不了解.只看懂了最后一段,进程间通信(IPC)内容被组织成了三个部分: (1)classical IPC : pipes, FIFOs, messa ...
- 第一篇 Postman的初级使用之设置环境快速切换生成环境与测试环境
POSTMAN是有谷歌的开源工具,在开发调试.测试执行过程中使用频率非常广泛,本文将记录一些postman在测试中常见的一些配置和使用方法 一.基本的页面区域 略,很简单,大家都会看,再有,学习下面的 ...
- Java中的while(true)
while(true)是一个无限循环 在内部用break或return退出循环,否则一直循环
- 05-Mysql数据库----补充内容
数据库命名规则: 数据库命名规则: 可以由字母.数字.下划线.@.#.$ 区分大小写 唯一性 不能使用关键字如 create select 不能单独使用数字 最长128位 # 基本上跟python或者 ...
- 机器学习/逻辑回归(logistic regression)/--附python代码
个人分类: 机器学习 本文为吴恩达<机器学习>课程的读书笔记,并用python实现. 前一篇讲了线性回归,这一篇讲逻辑回归,有了上一篇的基础,这一篇的内容会显得比较简单. 逻辑回归(log ...
- NLP系列-中文分词(基于统计)
上文已经介绍了基于词典的中文分词,现在让我们来看一下基于统计的中文分词. 统计分词: 统计分词的主要思想是把每个词看做是由字组成的,如果相连的字在不同文本中出现的次数越多,就证明这段相连的字很有可能就 ...
- 【转】V8 之旅: 垃圾回收器
垃圾回收器是一把十足的双刃剑.其好处是可以大幅简化程序的内存管理代码,因为内存管理无需程序员来操作,由此也减少了(但没有根除)长时间运转的程序的内存泄漏.对于某些程序员来说,它甚至能够提升代码的性能. ...
- 【翻译】ASP.NET Core 文档目录
微软官方CORE 2.0正式版中文文档已经出来了,地址:https://docs.microsoft.com/zh-cn/aspnet/core/ 简介 入门 创建一个Web应用程序 创建一个Web ...