题面

洛谷

题解

30pts

爆搜即可。

100pts

题意描述里有一句:"对每张图片\(i\),小\(D\)都最多只记住了某一张质量不比\(i\)差的另一张图片\(K_i\)。"

即只有一个父亲,且\(m\leq n\),所以建树,容易想到树形\(dp\),

对于"\(=\)"的,直接用并查集将之看成一个点,

对于"\(<\)"的,将小的连一条到大的点的边,

然后不一定是一棵树,可能是森林,所以建一个超级根节点连起来。

设\(f[u][i]\)表示以\(u\)为根,分成\(i\)段(即共有\(y-1\)个小于,每个小于两边所有图片质量相等)的方案数,

按照树形\(dp\)转移,则有

\[f[u][i]=\sum f'[u][j]\times f[v][k]\times num
\]

\(num\)表示将\(j\)段和\(k\)段合并的方案数,如何求呢?

设\(f[u]\)的质量序列为\(A\),\(f'[u]\)的质量序列为\(B\),\(f[v]\)的质量序列为\(C\)。

\(A\)中的每一段可以只包含\(B\)中的一段,可以只包含\(C\)中的一段,也可以有\(B\)和\(C\)中各一段合并而成,但不能为空。特殊地,\(A\)的第一段只能包含节点\(u\)。

因为\(f[u]\)与\(f'[u]\)都包含\(u\)那一段,所以相当于从\(i-1\)中选\(j-1\)个合并,方案数为\(C_{i-1}^{j-1}\),

然后把\(C\)中的\(i-j\)段放到\(A\)中剩下的位置,使每一段都不为空。现在\(C\)中还剩下\(k-i+j\)个段,他们需要与\(B\)中的段合并,方案数为\(C_{j-1}^{k-i+j}\)。

\[\therefore num=C_{i-1}^{j-1}\times C_{j-1}^{k-i+j}
\]

然后

\[Ans=\sum f[n+1][i]
\]

最后复杂度为\(O(n^3)\)。

代码

#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <algorithm>
using namespace std;
const int Mod = 1e9 + 7;
const int MAX_N = 105;
struct Graph { int to, next; } e[MAX_N << 1]; int fir[MAX_N], e_cnt;
void clearGraph() { memset(fir, -1, sizeof(fir)); e_cnt = 0; }
void Add_Edge(int u, int v) { e[e_cnt] = (Graph){v, fir[u]}; fir[u] = e_cnt++; }
int pa[MAX_N];
int getf(int x) { return pa[x] == x ? x : pa[x] = getf(pa[x]); }
int N, M, X[MAX_N], Y[MAX_N], cnt[MAX_N], C[MAX_N][MAX_N];
bool isroot[MAX_N];
int f[MAX_N][MAX_N], size[MAX_N];
void dfs(int x) {
size[x] = f[x][1] = 1;
for (int i = fir[x]; ~i; i = e[i].next) {
int v = e[i].to; dfs(v);
size[x] += size[v];
for (int j = size[x]; j >= 1; j--) {
int res = 0;
for (int k = 1; k <= min(size[x] - size[v], j); k++)
for (int l = max(1, j - k); l <= size[v]; l++)
res = (res + 1ll * f[x][k] * f[v][l] % Mod
* C[j - 1][k - 1] % Mod
* C[k - 1][l - j + k] % Mod) % Mod;
f[x][j] = res;
}
}
}
int main () {
#ifndef ONLINE_JUDGE
freopen("cpp.in", "r", stdin);
#endif
clearGraph();
scanf("%d%d", &N, &M);
C[0][0] = 1;
for (int i = 1; i <= N + 1; i++) C[i][0] = 1, C[i][i] = 1;
for (int i = 2; i <= N + 1; i++)
for (int j = 1; j < i; j++)
C[i][j] = (C[i - 1][j - 1] + C[i - 1][j]) % Mod;
for (int i = 1; i <= N; i++) pa[i] = i; for (int i = 1; i <= M; i++) {
char ch[5];
scanf("%d%s%d", X + i, ch, Y + i);
if (ch[0] == '=') pa[getf(Y[i])] = getf(X[i]);
}
for (int i = 1; i <= M; i++) X[i] = getf(X[i]), Y[i] = getf(Y[i]);
for (int i = 1; i <= M; i++) {
if (X[i] == Y[i]) continue;
if (getf(X[i]) != getf(Y[i])) {
Add_Edge(X[i], Y[i]), cnt[Y[i]]++, isroot[X[i]] = 1;
pa[getf(Y[i])] = getf(X[i]);
} else return puts("0") & 0;
}
for (int i = 1; i <= N; i++) if (isroot[i] && !cnt[i]) Add_Edge(N + 1, i);
dfs(N + 1);
int ans = 0;
for (int i = 1; i <= size[N + 1]; i++) ans = (ans + f[N + 1][i]) % Mod;
printf("%d\n", ans);
return 0;
}

【LG3240】[HNOI2015]实验比较的更多相关文章

  1. 【BZOJ4013】[HNOI2015]实验比较(动态规划)

    [BZOJ4013][HNOI2015]实验比较(动态规划) 题面 BZOJ 洛谷 题解 看题目意思就是给你一棵树,连边表示强制顺序关系.然后你要给点染色,在满足顺序关系的情况下,将序列染成若干个颜色 ...

  2. 4013: [HNOI2015]实验比较

    4013: [HNOI2015]实验比较 链接 分析: 首先把等号用并查集合并起来. 由于只存在最多一个质量不比i差的数,发现这是森林.若x<y,连边x->y.于是建虚拟根节点0. 然后树 ...

  3. [BZOJ4013][HNOI2015]实验比较(树形DP)

    4013: [HNOI2015]实验比较 Time Limit: 5 Sec  Memory Limit: 512 MBSubmit: 756  Solved: 394[Submit][Status] ...

  4. bzoj 4013: [HNOI2015]实验比较

    Description 小D 被邀请到实验室,做一个跟图片质量评价相关的主观实验.实验用到的图片集一共有 N 张图片,编号为 1 到 N.实验分若干轮进行,在每轮实验中,小 D会被要求观看某两张随机选 ...

  5. [HNOI2015]实验比较

    Description 小D 被邀请到实验室,做一个跟图片质量评价相关的主观实验.实验用到的图片集一共有 N 张图片,编号为 1 到 N.实验分若干轮进行,在每轮实验中,小 D会被要求观看某两张随机选 ...

  6. P3240 [HNOI2015]实验比较 树形DP

    \(\color{#0066ff}{ 题目描述 }\) 小D 被邀请到实验室,做一个跟图片质量评价相关的主观实验.实验用到的图片集一共有 \(N\) 张图片,编号为 \(1\) 到\(N\).实验分若 ...

  7. BZOJ4013 : [HNOI2015]实验比较

    首先用并查集将等号缩点,然后拓扑排序判断有没有环,有环则无解,否则通过增加超级源点$0$,可以得到一棵树. 设$f[x][y]$表示$x$子树里有$y$种不同的数字的方案数,由底向上DP. 对于当前点 ...

  8. luogu P3240 [HNOI2015]实验比较

    传送门 首先根据题目条件,题目中如果是=的点可以缩起来,然后\(a<b\)连边\(a\rightarrow b\),而且所有点入度为最多1,那么判掉有环的不合法情况,题目中的依赖关系就是一颗外向 ...

  9. 【BZOJ】4013: [HNOI2015]实验比较

    题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=4013 中第i 条涉及的图片对为(KXi, Xi),判断要么是KXi < Xi ,要么 ...

随机推荐

  1. 简易使用UILabel的富文本

    简易使用UILabel的富文本 使用效果: 源码: NSString+YX.h    NSString+YX.m // // NSString+YX.h // YXKit // // Copyrigh ...

  2. Windows与Linux 互相访问,挂载过程

    开始使用Linux时浏览器无法访问,多次尝试以失败告终,果断放弃自我动手, 找了大神帮助,弄了半天终于可以访问.但是之前在Windows下的文件也不能放弃,从大神那里那里文档,然后进行尝试 1.在Wi ...

  3. ZT Android 4.2蓝牙介绍

    Android 4.2蓝牙介绍 分类: Android开发系列 2013-06-27 14:16 7110人阅读 评论(22) 收藏 举报 目录(?)[-] Android 42蓝牙介绍 一  蓝牙规 ...

  4. django中session的存储位置

    django-session 存放位置 设置session的保存位置,有三种方法: 保存在关系数据库(db) 保存在缓存数据库(cache) 或者 关系+缓存数据库(cache_db) 保存在文件系统 ...

  5. Spring Boot 以 war 方式部署

    Spring Boot 默认自带了一个嵌入式的 Tomcat 服务器,可以以jar方式运行,更为常见的情况是需要将 Spring Boot 应用打包成一个 war 包,部署到 Tomcat.Jerry ...

  6. Cloudera Manager 4.6 安装部署hadoop CDH集群

    Cloudera Manager 4.6 安装详解 1. Cloudera Manager介绍 1.1. 功能介绍 Cloudera Manager是一个针对hadoop集群的管理工具,功能包括:cd ...

  7. loj6119 「2017 山东二轮集训 Day7」国王

    题目描述 在某个神奇的大陆上,有一个国家,这片大陆的所有城市间的道路网可以看做是一棵树,每个城市要么是工业城市,要么是农业城市,这个国家的人认为一条路径是 exciting 的,当且仅当这条路径上的工 ...

  8. 在centos上安装smplayer播放器

    Smplayer是一个非常好用的媒体播放器.可以支持大部分的视频和音频文件.它支持音频轨道切换.允许调节亮度.对比度.色调.饱和度.伽玛值,按照倍速.4倍速等多种速度回放.还可以进行音频和字幕延迟调整 ...

  9. 基于VUE.JS的移动端框架Mint UI

    Mint UI GitHub:github.com/ElemeFE/mint 项目主页:mint-ui.github.io/# Demo:elemefe.github.io/mint- 文档:mint ...

  10. java学习笔记-JavaWeb篇二

    JavaWEB篇二 45 HttpSession概述46 HttpSession的生命周期 47 HttpSession常用方法示例48 HttpSessionURL重写 49 HttpSession ...