洛谷P1446/BZOJ1004 Cards Burnside引理+01背包
题意:有n张牌,有R+G+B=n的3种颜色及其数量,要求用这三种颜色去染n张牌。n张牌有m中洗牌方式,问在不同洗牌方式下本质相同的染色方案数。
解法:这道题非常有意思,题解参考Hzwer学长的。我这里再总结一下:
看到本质相同的染色方案我们很容易会想到Burnside引理和Polya定理,但是这题不能用Polya定理,为什么?因为一般的Ployd染色的颜色个数是没有限制的,于是当循环节为l颜色为c时候,方式数就是c^l(就是因为一个循环方案要相同所以染的颜色也要相同)。但是此题颜色个数有限制,不能直接每个格子有c种选择,所以不能使用Polyd定理。
那现在我们还是得保证一个循环内颜色相同但又不用Ployd呢?我们使用Burnside引理:可以想象成这样,我们必须要有R个红色,G个绿色,B个蓝色,且每一个循环节我们可以选择它染成R/G/B。那这不就是一个01背包模型,每个循环节就是一个物品,RGB就是容量限制,那么我们就可以用01背包计算方案数即可。
细节见代码及其注释。
#include<bits/stdc++.h>
using namespace std;
typedef long long LL;
const int N=;
int n,r,g,b,m,P,a[],d[]; void exgcd(int a,int b,int& d,int& x,int& y) { //ax+by=gcd(a,b)
if (!b) { d=a;x=;y=; }
else { exgcd(b,a%b,d,y,x); y-=x*(a/b); }
} bool vis[];
LL dp[][N][N][N]; //dp[l][i][j][k]代表前l个循环节组成i个Rj个Gk个B的方案数
LL solve() { //每次计算置换群a的方案数(相当于做一次01背包)
for (int i=;i<=n;i++) vis[i]=;
int num=,now=;
for (int i=;i<=n;i++) { //统计循环节
if (vis[i]) continue;
d[++num]=; now=i; //循环节数量/大小
vis[now]=;
while (!vis[a[now]]) {
d[num]++;
vis[a[now]]=;
now=a[now];
}
}
for (int l=;l<=num;l++) for (int i=;i<=r;i++) for (int j=;j<=g;j++) for (int k=;k<=b;k++)
dp[l][i][j][k]=;
dp[][][][]=; //初始化
for (int l=;l<=num;l++) //循环节个数相当于物品个数
for (int i=;i<=r;i++)
for (int j=;j<=g;j++)
for (int k=;k<=b;k++) {
if (i>=d[l]) dp[l][i][j][k]=(dp[l][i][j][k]+dp[l-][i-d[l]][j][k])%P;
if (j>=d[l]) dp[l][i][j][k]=(dp[l][i][j][k]+dp[l-][i][j-d[l]][k])%P;
if (k>=d[l]) dp[l][i][j][k]=(dp[l][i][j][k]+dp[l-][i][j][k-d[l]])%P;
}
return dp[num][r][g][b];
} int main()
{
scanf("%d%d%d%d%d",&r,&g,&b,&m,&P);
n=r+g+b;
LL ans=;
for (int i=;i<=m;i++) {
for (int j=;j<=n;j++) scanf("%d",&a[j]);
ans+=solve(); //累加所有置换方案数
}
for (int i=;i<=n;i++) a[i]=i;
ans+=solve();
int x,y,d; exgcd(m+,P,d,x,y);
x=(x%P+P)%P; //求出m+1再模P下逆元
cout<<ans*x%P<<endl;
return ;
}
洛谷P1446/BZOJ1004 Cards Burnside引理+01背包的更多相关文章
- 洛谷 P4708 - 画画(Burnside 引理+组合数学)
洛谷题面传送门 神仙题 %%%%%%%%%%%%%%%%%%%% 题解搬运人来了 首先看到本质不同(无标号)的图计数咱们可以想到 Burnside 引理,具体来说,我们枚举一个排列 \(p\),并统计 ...
- 洛谷 P1446 [HNOI2008]Cards 解题报告
P1446 [HNOI2008]Cards 题目描述 小春现在很清闲,面对书桌上的\(N\)张牌,他决定给每张染色,目前小春只有\(3\)种颜色:红色,蓝色,绿色.他询问Sun有多少种染色方案,Sun ...
- luogu P1446 [HNOI2008]Cards burnside引理 置换 不动点
LINK:Cards 不太会burnside引理 而这道题则是一个应用. 首先 一个非常舒服的地方是这道题给出了m个本质不同的置换 然后带上单位置换就是m+1个置换. burnside引理: 其中D( ...
- 洛谷P1441 砝码称重 枚举 + 01背包
显然,n<=20, m<=4 的数据范围一眼爆搜. 直接搜索一下不用哪4个砝码,再做一遍01背包即可. 可能是本人太菜鸡,01背包部分调了半天QAQ-- #include<cstdi ...
- 洛谷P1164小A点菜(01背包)
题目背景 uim神犇拿到了uoi的ra(镭牌)后,立刻拉着基友小A到了一家……餐馆,很低端的那种. uim指着墙上的价目表(太低级了没有菜单),说:“随便点”. 题目描述 不过uim由于买了一些辅(e ...
- 洛谷 P2871 [USACO07DEC]手链Charm Bracelet && 01背包模板
题目传送门 解题思路: 一维解01背包,突然发现博客里没有01背包的板子,补上 AC代码: #include<cstdio> #include<iostream> using ...
- 洛谷P1446 [HNOI2008]Cards
置换群+dp #include<cstdio> #include<cstdlib> #include<algorithm> #include<cstring& ...
- 洛谷 P1282 多米诺骨牌("01"背包)
传送门 https://www.cnblogs.com/violet-acmer/p/9852294.html 参考资料: [1]:https://blog.csdn.net/Darost/artic ...
- 洛谷——2871[USACO07DEC]手链Charm Bracelet——01背包
题目描述 Bessie has gone to the mall's jewelry store and spies a charm bracelet. Of course, she'd like t ...
随机推荐
- java实现简单的控制台的计算器
要用面向对象的思维写. //我是代码的搬运工import java.util.Scanner;public class Main { public static void main(String[] ...
- python学习笔记(六)函数
1.函数是什么? 定义:函数是指一组语句的集合通过一个名字(函数名)封装起来,只需调用函数名即可. 2.函数的好处: 简化代码 提高代码的复用性 代码可扩展 3.python中函数的定义: 定义函数使 ...
- Dubbo学习-7-dubbo配置文件优先级
Dubbo配置加载流程 根据驱动方式的不同(比如Spring或裸API编程)配置形式上肯定会有所差异,具体参考XML配置.Annotation配置.API配置三篇文档.除了外围驱动方式上的差异,Dub ...
- 2018年第九届山东省ACM省赛总结
去年打完区域赛之后,面对着两个队友都去找实习的情况,我自己对今年省赛还是有点慌的.不只一次的像我的队友说明自己很慌,但是老曹跟会长都说:“没事,慌啥!”前几场训练赛因为老曹跟秋洁有面试有时候只能一个人 ...
- UVA10870 Recurrences (矩阵快速幂及构造方法详解)
题意: F(n) = a1 * F(n-1) + a2 * F(n-2)+ ···· + ad * F(n-d). 求给你的n . 很明显这是一道矩阵快速幂的题目. 题解: [Fn-1, Fn-2, ...
- 台哥原创:java 俄罗斯方块源码
大四的时候,用java开发,耗时一周 界面参照当时用的联想手机里的俄罗斯方块 这里的级别,标识难度,1是初级,方块下降速度很慢,5是最高级,下降速度最快 得分:每消除一行,会给10分,同时消除 ...
- 10个最容易犯的Python开发错误
10个最容易犯的Python开发错误 转载 2017年09月25日 16:54:36 标签: python / 大数据 / 大讲台 Python是一门简单易学的编程语言,语法简洁而清晰,并且拥有丰 ...
- ADO.NET-EF:ADO.NET Entity Framework 百科
ylbtech-ADO.NET-EF:ADO.NET Entity Framework 百科 ADO.NET Entity Framework 是微软以 ADO.NET 为基础所发展出来的对象关系对应 ...
- JavaScript-[[prototype]]的另一种理解
[[prototype]]简介 javascript 中每一个对象都会有一个特殊的内置属性[[prototype]],这个就是对其他对象对引用.有了这个作为基础去关联其他对象,就能理解继承机制.Chr ...
- Linux运维知识之linux shell date 用当天时间做备份文件名
本文主要向大家介绍了Linux运维知识之linux shell date 用当天时间做备份文件名,通过具体的内容向大家展现,希望对大家学习Linux运维知识有所帮助. #!/bin/bash #dat ...