[BZOJ1004][HNOI2008]Cards 群论+置换群+DP
题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=1004
首先贴几个群论相关定义和引理。
群:G是一个集合,*是定义在这个集合上的一个运算。
如果满足以下性质,那么(G, *)是一个群。
1)封闭性,对于任意 a, b 属于 G, a * b 属于 G
2)结合律, a * b * c = a * (b * c)
3)单位元,在 G 中存在一个单位元 e ,使得对于 G 中任意的 a , a * e = e * a = a
4)逆元, 对于 G 中任意的 a ,在 G 中存在 b , 使得 a * b = e , 其中 b 叫做 a 的逆元
比如在模一个数意义下的整数加法就是一个群。
满足交换律的群是交换群,又叫阿贝尔群。
置换:可以用 (a1 -> b1, a2 -> b2, ... , an -> bn) 表示一个置换,其中 a1, ... , an 和 b1, ..., bn 都是1 到 n 的一个排列;
如果一些置换和它们的叠加运算构成一个群,就把它们叫做一个置换群。
在置换群中的 Burnside 引理:如果按照一定要求,要对1到n 的位置染色,那么本质不同的染色方案数为置换群中每个置换的不动染色方案数的平均数。
来解释以下,本质不同的染色方案是指,两个染色方案不能通过置换群中的任意置换变换使其相同,那么它们就是本质不同的。
某个置换的不动染色方案数是指,用这个置换变换之后没有发生变化的染色方案。
那么我们就是要求出每个置换的不动染色方案数。
Polya定理,如果是用k种颜色染色,那么对于置换 P 来说,它的不动染色方案数为 k^(L(P)), 其中L(P)为置换P的循环节数。
由于这道题中有颜色数目的限制,我们不能直接套Polya定理,但是可以把每个循环节当作一种物品,用背包求方案数。
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
int inline readint(){
int Num;char ch;
while((ch=getchar())<''||ch>'');Num=ch-'';
while((ch=getchar())>=''&&ch<='') Num=Num*+ch-'';
return Num;
}
int Sr,Sb,Sg,n,m,mod;
int quick_pow(int x,int y){
int base=x,sum=;
while(y){
if(y&) sum=sum*base%mod;
base=base*base%mod;
y>>=;
}
return sum;
}
int fm[][],cnt[],f[/][/][/];
bool vis[];
int dp(int x){
int tot=;
memset(vis,false,sizeof(vis));
memset(cnt,,sizeof(cnt));
memset(f,,sizeof(f));
for(int i=;i<=n;i++){
if(!vis[i]){
int j=i;
tot++;
while(!vis[fm[x][j]]){
vis[fm[x][j]]=true;
cnt[tot]++;
j=fm[x][j];
}
}
}
f[][][]=;
for(int i=;i<=tot;i++)
for(int j=Sr;j>=;j--)
for(int k=Sb;k>=;k--)
for(int t=Sg;t>=;t--){
if(j>=cnt[i]) f[j][k][t]=(f[j][k][t]+f[j-cnt[i]][k][t])%mod;
if(k>=cnt[i]) f[j][k][t]=(f[j][k][t]+f[j][k-cnt[i]][t])%mod;
if(t>=cnt[i]) f[j][k][t]=(f[j][k][t]+f[j][k][t-cnt[i]])%mod;
}
return f[Sr][Sb][Sg];
}
int main(){
Sr=readint();
Sb=readint();
Sg=readint();
m=readint();
mod=readint();
n=Sr+Sb+Sg;
for(int i=;i<=m;i++)
for(int j=;j<=n;j++)
fm[i][j]=readint();
m++;
for(int i=;i<=n;i++) fm[m][i]=i;
int ans=;
for(int i=;i<=m;i++) ans+=dp(i);
ans=ans*quick_pow(m,mod-)%mod;
printf("%d\n",ans);
return ;
}
[BZOJ1004][HNOI2008]Cards 群论+置换群+DP的更多相关文章
- bzoj1004: [HNOI2008]Cards(burnside引理+DP)
题目大意:3种颜色,每种染si个,有m个置换,求所有本质不同的染色方案数. 置换群的burnside引理,还有个Pólya过几天再看看... burnside引理:有m个置换k种颜色,所有本质不同的染 ...
- bzoj1004 [HNOI2008]Cards 置换群+背包
[bzoj1004][HNOI2008]Cards 2014年5月26日5,3502 Description 小春现在很清闲,面对书桌上的N张牌,他决定给每张染色,目前小春只有3种颜色:红色,蓝色,绿 ...
- [bzoj1004][HNOI2008][Cards] (置换群+Burnside引理+动态规划)
Description 小春现在很清闲,面对书桌上的N张牌,他决定给每张染色,目前小春只有3种颜色:红色,蓝色,绿色.他询问Sun有多少种染色方案,Sun很快就给出了答案.进一步,小春要求染出Sr张红 ...
- BZOJ1004: [HNOI2008]Cards(Burnside引理 背包dp)
Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 4255 Solved: 2582[Submit][Status][Discuss] Descript ...
- BZOJ 1004: [HNOI2008]Cards [Polya 生成函数DP]
传送门 题意:三种颜色,规定使用每种颜色次数$r,g,b$,给出一个置换群,求多少种不等价着色 $m \le 60,\ r,g,b \le 20$ 咦,规定次数? <组合数学>上不是有生成 ...
- BZOJ1004 HNOI2008 Cards Burnside、背包
传送门 在没做这道题之前天真的我以为\(Polya\)可以完全替代\(Burnside\) 考虑\(Burnside\)引理,它要求的是对于置换群中的每一种置换的不动点的数量. 既然是不动点,那么对于 ...
- 【BZOJ】1004: [HNOI2008]Cards(置换群+polya+burnside)
http://www.lydsy.com/JudgeOnline/problem.php?id=1004 学习了下polya计数和burnside引理,最好的资料就是:<Pólya 计数法的应用 ...
- BZOJ1004 [HNOI2008]Cards 【burnside定理 + 01背包】
题目链接 BZOJ1004 题解 burnside定理 在\(m\)个置换下本质不同的染色方案数,等于每种置换下不变的方案数的平均数 记\(L\)为本质不同的染色方案数,\(m\)为置换数,\(f(i ...
- bzoj1004 [HNOI2008]Cards【Burnside/Polya】
传送门:http://www.lydsy.com/JudgeOnline/problem.php?id=1004 一道好题,但并不是好在融合了三个“考点”(计数,背包dp,逆元),其实背包dp以及求逆 ...
随机推荐
- Python函数参数传递
Python中函数参数的传递是采用传值方式,但是和C/C++有所不同 C/C++方式 void fun(int a) { a = 10; } void main() { int c =3; fun(c ...
- Angular45
Angular 4 Tutorial for Beginners: Learn Angular 4 from Scratch https://www.youtube.com/watch?v=k5E2A ...
- Linux 简单的Shell输出
echo:用于输出指定字符串或用于在Shell中打印Shell变量的值 语法格式:echo [选项] [参数] -n:不输出换行 linlin@ubuntu:~/linlin/text$ ...
- MJRefresh实现刷新(使用它的Block方法)
MJRefresh实现刷新(使用它的Block方法) // // YFMVCPostListViewController.m // iOS122 // // Created by 颜风 on 15 ...
- method.invoke()使用
public Object invoke(Object obj, Object... args) throws IllegalAccessException, IllegalArgumentExcep ...
- Delphi XE10调用WebService服务获取图片验证码
最近做了一个程序,需要使用图片验证码,百度一下,网上一大把免费的WebService服务,随意找一个用用,效果还可以.WebService地址:http://www.webxml.com.cn/Web ...
- HDU - 4333 Revolving Digits(拓展kmp+最小循环节)
1.给一个数字字符串s,可以把它的最后一个字符放到最前面变为另一个数字,直到又变为原来的s.求这个过程中比原来的数字小的.相等的.大的数字各有多少. 例如:字符串123,变换过程:123 -> ...
- bash: crontab: command not found
操作步骤 1. 确认crontab是否安装: 执行 crontab 命令如果报 command not found,就表明没有安装 2. 安装 crontab 执行 yum install -y vi ...
- xcode 8.1 (8B62)真机调试配置
1.点击菜单栏中的Xcode->Preferences->Accounts,如图: 点击上图左下角中的“+”号,登陆一个Apple id(前提已经有了一个apple id账号), 2.然后 ...
- 【JSOI 2008】 最大数
[题目链接] 点击打开链接 [算法] 很明显,我们可以用线段树解决此题 只需维护区间最值就可以了 [代码] #include<bits/stdc++.h> using namespace ...