NOIP2016 “西湖边超萌小松鼠” 模拟赛
总的来说,这套题的难度比较接近近些年来Day1的真实难度,认为非常值得一打
GotoAndPlay
题目大意
询问这个图上是否存在一种跳法,能跳到这个图上的每一个点
题目解析
犯了个低级错误,双向边忘记*2,最后两个点RE了
因为题目告知是“跳两次”,所以很容易想到将这个图分成“奇数点”和“偶数点”,那么所有“奇点“和所有“偶点”是能够独立相互到达的。
换句话来说,只要有一个点既属于“偶点“又属于”奇点”,那整个图都能相互到达了(这就是二分图)
因此我们先在原图做一遍DFS/BFS,标记初始标号
如果有一个点我们要对他进行标记两种不同标号,那整个图就完全可以到达了
如果假的一条边,连通了两个标记不一样的点,那“奇点”就可以到达“偶点”了,及那整个图就完全可以到达了
#include <cstdio>
#include <iostream>
#include <cstring>
using namespace std;
#define qword long long
#define seta(x, y) memset(x, y, sizeof(x))
#define forn(i, n) for (int i = 1; i <= (int)(n); ++ i)
#define rep(i, s, t) for (int i = (int)(s); i <= (int)(t); ++ i)
const int maxn = 4e5 + 10;
inline void File() {
const string task = "GotoAndPlay";
freopen((task + ".in").data(), "r", stdin);
freopen((task + ".out").data(), "w", stdout);
}
int n, m;
int to[maxn], head[maxn], next[maxn];
int color[maxn];
bool flag = false;
int cnt = 0;
inline void addEdge(int x, int y) {
to[++cnt] = y;
next[cnt] = head[x];
head[x] = cnt;
}
inline void dfs(int x, int c) {
if (color[x] != -1 && color[x] != c) {flag = 1; return;}
color[x] = c;
for (int i = head[x]; i; i = next[i]) {
if (color[to[i]] == -1) dfs(to[i], (~c) & 1);
//else if (color[to[i]] == color[i]) flag = true;
}
}
inline void query(int x) {
int a, b;
scanf("%d %d", &a, &b);
if (color[a] == color[b] || flag) {
printf("Yes\n"); return;
}
printf("No\n"); return;
}
int main() {
//File();
scanf("%d %d", &n, &m);
int x, y;
forn(i, m) {
scanf("%d %d", &x, &y);
addEdge(x, y); addEdge(y, x);
}
forn(i, n) color[i] = -1; // Init
dfs(1, 0);
int p;
scanf("%d", &p);
forn(i, p) query(p);
return 0;
}
StopAllSounds
题目分析
一开始没有条理的乱搞,浪费了5分钟。。。
因为横只为2,所以我们可以分析出当前这只积木落下后最后的状态。
因为发现当前积木落下之后,下面所有的积木构成已经对后续没有影响,这满足了无后效性这一DP的基本条件
于是我们做一个dp,用 $ f[i][j] $ 表示现在最高的积木在 $ i $ 这个高度,最后一个状态是 $ j $ (这里我用1-6表示6中最终状态)
最后进行转移就行了
#include <cstdio>
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
#define qword long long
#define seta(x, y) memset(x, y, sizeof(x))
#define forn(i, n) for (int i = 1; i <= (int)(n); ++ i)
#define rep(i, s, t) for (int i = (int)(s); i <= (int)(t); ++ i)
inline void File() {
const string task = "StopAllSounds";
freopen((task + ".in").data(), "r", stdin);
freopen((task + ".out").data(), "w", stdout);
}
const int mod = 1e9 + 7;
int n;
long long dp[1001000][7];
int main() {
File();
scanf("%d",&n);
memset(dp, 0, sizeof(dp));
forn(i, 6) dp[3][i] = 1;
dp[3][4] = 0; dp[2][4] = 1;
rep(i, 4, n) {
dp[i][1] = (dp[i-3][1] + dp[i-2][2] + dp[i-2][3] + dp[i-3][4] + dp[i-2][5] + dp[i-3][6]) % mod;
dp[i][2] = (dp[i-2][1] + dp[i-3][2] + dp[i-3][3] + dp[i-3][4] + dp[i-3][5] + dp[i-3][6]) % mod;
dp[i][3] = (dp[i-3][1] + dp[i-2][2] + dp[i-2][3] + dp[i-3][4] + dp[i-2][5] + dp[i-3][6]) % mod;
dp[i][4] = (dp[i-2][1] + dp[i-2][2] + dp[i-2][3] + dp[i-2][4] + dp[i-2][5] + dp[i-2][6]) % mod;
dp[i][5] = (dp[i-3][1] + dp[i-3][2] + dp[i-3][3] + dp[i-3][4] + dp[i-3][5] + dp[i-3][6]) % mod;
dp[i][6] = (dp[i-3][1] + dp[i-2][2] + dp[i-2][3] + dp[i-3][4] + dp[i-1][5] + dp[i-3][6]) % mod;
}
qword ans = 0;
rep(i, 2, n) forn(j, 6)
ans += dp[i][j] % mod;
printf("%lld", (ans + 1) % mod);
return 0;
}
UpdateAfterEvent
题目分析
这道题是这里面唯一一个达到了提高+/省选难度的题
首先思考如何将问题所求:期望的松鼠对数 转化为我们较为熟悉和擅长入手的东西。
大家能够发现,尽管可能大家最先想到的计算松鼠对数的方法,是根据树上的松鼠总数 $ x $,通过 $ x * (x - 1) / 2$ 来得到。但不妨考虑一下一个更一般的方法:
枚举一只松鼠,再枚举另一只松鼠,如果它们在同一棵树上则答案加一。
从这个方法中能够得到的启示是:松鼠对数这个量实际上是相对独立的,即与这两只松鼠之外的量并无直接的关系。
这样就避免了我们陷入一味考虑如何计算“松鼠期望总数”的错误方向了。
相似地,当我们计算期望时,也存在这样一个方法:
枚举一只松鼠 $ A $ ,再枚举另一只松鼠 $ B $ ,考虑它们同时存在在树i上的情况。
假设松鼠\(A\)在树i上的概率为 $ P(A, i) $ , 松鼠B在树i上的概率为 $ P(B, i) $
则它们同时存在于树i上的概率为 $ P(A, i) * P(B, i) $
而这一事件构成了“1对结束时在同一棵树上的松鼠”
因此对答案的贡献是 $ P(A, i) * P(B, i) * 1 $
我们只需要对于每一对松鼠枚举一下树 $ i $ ,然后对这些东西求和计入答案就可以了。
考虑如何计算 $ P(A,i) $ 。我们不妨假设 $ f(i, j) $ 为一只松鼠从点i出发,在点j停下的概率。
当 $ T = 0\(时,\) f [i][i] $ 均为1.0,每过一个单位时间时,考虑 $ f[i][j] $ 即松鼠当前在 $ j $ 时的概率
根据题中的描述向 $ j $的相邻点转移。
这样能够得到所有 $ T \le 30 $ 的分数
观察可知,每次的转移事实上都是一样的。于是我们可以使用矩阵乘法来优化这个转移过程。
时间复杂度 $ O(n^3logT) $ ,这部分有 $ 30 $ 的数据。
30%的部分分是给 $ n ^ 2 $ 计算期望的方法。直接枚举两个位置和终点的位置计算是 $ n ^ 3 $ 的,但是我们在枚举两个位置的时候,可以维护一下前缀和,累计的时候直接计算与前缀和的乘积。就可以将计算期望的过程优化到 $ n ^ 2 $ 了。
NOIP2016 “西湖边超萌小松鼠” 模拟赛的更多相关文章
- 小奇模拟赛9.13 by hzwer
2015年9月13日NOIP模拟赛 by hzwer (这是小奇=> 小奇挖矿(explo) [题目背景] 小奇要开采一些矿物,它驾驶着一台带有钻头(初始能力值w)的飞船,按既定路线依次飞 ...
- [模拟赛] StopAllSounds
Description 小松鼠开心地在树之间跳跃着,突然她停了下来.因为眼前出现了一个 拿着专克超萌小松鼠的法宝----超萌游戏机的游客! 超萌游戏机之所以拥有这个名字,是因为它的屏幕是一个n × 2 ...
- [模拟赛] GotoAndPlay
GotoAndPlay 10月3日,在杭州市西湖景区,一只小松鼠不停地接受一道道食物,花生. 玉米.饼干,可谓来者不拒,憨态可掬的模样吸引了众多围观者... Description 小松鼠终于吃撑了, ...
- 【20170521校内模拟赛】热爱生活的小Z
学长FallDream所出的模拟赛,个人感觉题目难度还是比较适中的,难度在提高+左右,可能比较接近弱省省选,总体来讲试题考查范围较广,个人认为还是很不错的. 所有试题如无特殊声明,开启-O2优化,时限 ...
- Java 第十一届 蓝桥杯 省模拟赛 小明的城堡
小明用积木搭了一个城堡. 为了方便,小明在搭的时候用的是一样大小的正方体积本,搭在了一个 n 行 m 列的方格图上,每个积木正好占据方格图的一个小方格. 当然,小明的城堡并不是平面的,而是立体的.小明 ...
- Java 第十一届 蓝桥杯 省模拟赛 小明植树(DFS)
小明植树 题目 问题描述 小明和朋友们一起去郊外植树,他们带了一些在自己实验室精心研究出的小树苗. 小明和朋友们一共有 n 个人,他们经过精心挑选,在一块空地上每个人挑选了一个适合植树的位置,总共 n ...
- 串门赛: NOIP2016模拟赛——By Marvolo 丢脸记
前几天liu_runda来机房颓废,顺便扔给我们一个网址,说这上面有模拟赛,让我们感兴趣的去打一打.一开始还是没打算去看一下的,但是听std说好多人都打,想了一下,还是打一打吧,打着玩,然后就丢脸了. ...
- 4.28 QBXT模拟赛
NOIP2016提高组模拟赛 ——By wangyurzee7 中文题目名称 迷妹 膜拜 换数游戏 英文题目与子目录名 fans mod game 可执行文件名 fans mod game 输入文件名 ...
- 冲刺$\mathfrak{CSP-S}$集训模拟赛总结
开坑.手懒并不想继续一场考试一篇文. 既没必要也没时间侧边栏的最新随笔题解反思相间也丑 而且最近越来越懒了竟然都不写题解了……开坑也是为了督促自己写题解. 并不想长篇大论.简要题解也得写啊QAQ. 目 ...
随机推荐
- ICMP重定向及其攻防技术
1.ICMP重定向概念: ICMP重定向技术,是用来提示主机改变自己的主机路由从而使路由路径最优化的一种ICMP报文.其概念理解的要义是原主机路由不是最佳路由,而其默认网关提醒主机优化自身的主机路由而 ...
- 聊聊对APM的理解
本文主要从以下几个列举对APM的认识: -什么是APM工具 -为什么要用APM工具,APM工具的价值在哪里: -什么样的APM工具适合于传统金融业: -如何用好APM工具: -精准告警 - ...
- rman备份的其它特性
1.7.3.1并发: 主要用于提高备份的速度,可以分为手动并发或自动并发 手动并发:通过分配多个通道并将文件指定到特定的通道 RMAN> run { 2> allocate channe ...
- Javaweb程序打包或exe执行文件
java程序的打包与发布 这里主要是讲解一下怎样将 Java程序打包成独立运行的exe程序包,以下这种方法应该是最佳的解决方案了.NetDuke的EXE程序包了是使用这种方案制作的.在操作步骤上还是比 ...
- 静态绑定 self 和 static的区别
后期静态绑定 自 PHP 5.3.0 起,PHP 增加了一个叫做后期静态绑定的功能,用于在继承范围内引用静态调用的类. 准确说,后期静态绑定工作原理是存储了在上一个“非转发调用”(non-forwar ...
- Iframe中子窗体给父窗体传值
<html> <head> <script type="text/javascript"> function GetData(data) { a ...
- LINQ中的连接(join)用法示例
Linq中连接主要有组连接.内连接.左外连接.交叉连接四种.各个用法如下. 1. 组连接 组连接是与分组查询是一样的.即根据分组得到结果. 如下例,根据publisther分组得到结果. 使用组连接的 ...
- 各大互联网企业Java面试题汇总,看我如何成功拿到百度的offer
前言 本人Java开发,5年经验,7月初来到帝都,开启面试经历,前后20天左右,主面互联网公司,一二线大公司或者是融资中的创业公司都面试过,拿了一些offer,其中包括奇虎360,最后综合决定还是去百 ...
- 解决ORA-29857:表空间中存在域索引和/或次级对象 & ORA-01940:无法删除当前连接的用户问题 分类: oracle sde 2015-07-30 20:13 8人阅读 评论(0) 收藏
今天ArcGIS的SDE发生了一点小故障,导致系统表丢失,所以需要重建一下SDE数据库,在删除SDE用户和所在的表空间过程中遇到下面两个ORA错误,解决方法如下: 1)删除表空间时报错:ORA-298 ...
- Java使用极小的内存完成对超大数据的去重计数,用于实时计算中统计UV
Java使用极小的内存完成对超大数据的去重计数,用于实时计算中统计UV – lxw的大数据田地 http://lxw1234.com/archives/2015/09/516.htm Java使用极小 ...