欢迎访问~原文出处——博客园-zhouzhendong

去博客园看该题解


题目传送门 - BZOJ1079


题目概括

  有n个木块排成一行,从左到右依次编号为1~n。你有k种颜色的油漆,其中第i种颜色的油漆足够涂ci个木块。所有油漆刚好足够涂满所有木块,即c1+c2+...+ck=n。相邻两个木块涂相同色显得很难看,所以你希望统计任意两个相邻木块颜色不同的着色方案。


题解

  一开始想状压dp,压每种颜色的剩余数。

  发现要超时。

  访问了hzwer大佬的博客,立刻恍然大悟。

  我们可以压每种剩余数的颜色个数!

  具体:

  dp[a][b][c][d][e][t]表示剩余1的颜色有a个,剩余2的颜色有b个,剩余3的颜色有c个,剩余4的颜色有d个,剩余5的颜色有e个,之前选择的那种颜色现在还剩t的方案总数。

  那么复杂度为165×6≈6500000,应该不会超时了。

  记忆化dfs比较好写,所以写了记忆化dfs。


代码

#include <cstring>
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cmath>
using namespace std;
typedef long long LL;
const LL mod=;
int k,tot[];
LL dp[][][][][][];
LL DP(int a,int b,int c,int d,int e,int t){
if (dp[a][b][c][d][e][t]!=-)
return dp[a][b][c][d][e][t];
if (a+b+c+d+e==)
return dp[a][b][c][d][e][t]=;
int A=a-(t==),B=b-(t==),C=c-(t==),D=d-(t==),E=e;
LL &res=dp[a][b][c][d][e][t];
res=;
if (a)
res+=A*DP(a-,b,c,d,e,);
if (b)
res+=B*DP(a+,b-,c,d,e,);
if (c)
res+=C*DP(a,b+,c-,d,e,);
if (d)
res+=D*DP(a,b,c+,d-,e,);
if (e)
res+=E*DP(a,b,c,d+,e-,);
return res%=mod;
}
int main(){
memset(dp,-,sizeof dp);
memset(tot,,sizeof tot);
scanf("%d",&k);
for (int i=,a;i<=k;i++){
scanf("%d",&a);
tot[a]++;
}
printf("%lld",DP(tot[],tot[],tot[],tot[],tot[],));
return ;
}

BZOJ1079 [SCOI2008]着色方案 动态规划的更多相关文章

  1. [luogu2476][bzoj1079][SCOI2008]着色方案【动态规划】

    题目描述 有n个木块排成一行,从左到右依次编号为1~n.你有k种颜色的油漆,其中第i种颜色的油漆足够涂ci个木块.所有油漆刚好足够涂满所有木块,即c1+c2+-+ck=n.相邻两个木块涂相同色显得很难 ...

  2. BZOJ1079:[SCOI2008]着色方案(DP)

    Description 有n个木块排成一行,从左到右依次编号为1~n.你有k种颜色的油漆,其中第i种颜色的油漆足够涂ci个木块. 所有油漆刚好足够涂满所有木块,即c1+c2+...+ck=n.相邻两个 ...

  3. BZOJ1079 [SCOI2008]着色方案 【dp记忆化搜索】

    题目 有n个木块排成一行,从左到右依次编号为1~n.你有k种颜色的油漆,其中第i种颜色的油漆足够涂ci个木块. 所有油漆刚好足够涂满所有木块,即c1+c2+-+ck=n.相邻两个木块涂相同色显得很难看 ...

  4. BZOJ1079: [SCOI2008]着色方案 (记忆化搜索)

    题意:有n个木块排成一行,从左到右依次编号为1~n.你有k种颜色的油漆,其中第i种颜色的油漆足够涂ci个木块. 所有油漆刚好足够涂满所有木块,即c1+c2+...+ck=n.相邻两个木块涂相同色显得很 ...

  5. 2018.10.20 bzoj1079: [SCOI2008]着色方案(多维dp)

    传送门 dp妙题. f[a][b][c][d][e][last]f[a][b][c][d][e][last]f[a][b][c][d][e][last]表示还剩下aaa个可以用一次的,还剩下bbb个可 ...

  6. BZOJ1079 [SCOI2008]着色方案[组合计数DP]

    $有a_{1}个1,a_{2}个2,...,a_{n}个n(n<=15,a_{n}<=5),求排成一列相邻位不相同的方案数.$ 关于这题的教训记录: 学会对于复杂的影响分开计,善于发现整体 ...

  7. bzoj1079: [SCOI2008]着色方案

    dp.以上次染色时用的颜色的数量和每种数量所含有的颜色作状态. #include<cstdio> #include<algorithm> #include<cstring ...

  8. 【记忆化搜索】bzoj1079 [SCOI2008]着色方案

    #include<cstring> #include<cstdio> using namespace std; #define MOD 1000000007 typedef l ...

  9. bzoj1079: [SCOI2008]着色方案

    ci<=5直接想到的就是5维dp了...dp方程YY起来很好玩...写成记忆化搜索比较容易 #include<cstdio> #include<cstring> #inc ...

随机推荐

  1. Android studio 自动导入(全部)包 import

    http://blog.csdn.net/buaaroid/article/details/44979629 1 Android studio 只有import单个包的快捷键:Alt+Enter.没有 ...

  2. Telnet Protocol Specification

    Network Working Group J. Postel Request for Comments: 854 J. Reynolds ISI Obsoletes: NIC 18639 May 1 ...

  3. Java——关于num++和++num

    public class num_add_add { public static void numAdd(){ int num = 10; int a = num++; System.out.prin ...

  4. 20155334 2016-2017-2 《Java程序设计》第九周学习总结

    20155334 2016-2017-2 <Java程序设计>第九周学习总结 教材学习内容总结 第十六章:整合数据库 16.1 JDBC入门 JDBC(Java DataBase Conn ...

  5. 设置PHPStorm 注释

    /** * Desc: xxx#if (${NAME}) * Class: ${NAME}#end#if (${NAMESPACE}) * Package: ${NAMESPACE}#end * Us ...

  6. python之join

    def aa(): print ('hh') ' print ('gg') ' print ('ff') ' c=['ss','aa','dd'] a='kk'.join(c) print (a)#s ...

  7. plist反序列化

    // //  ViewController.m //  03-plist文件的一个反序列化 // //  Created by jerry on 15/9/28. //  Copyright (c) ...

  8. ubuntu 14.04 安装 eclipse

    在安装 eclipse 之前必须先安装 jdk 1. 卸载默认的 jdk,以防安装出错 sudo apt-get purge openjdk* 2. 安装 jdk1.8.0_111 下载jdk1.8. ...

  9. TrimLeft TrimRight

    strming.TrimLeft();  //将字符串最前面的空格修整掉.当在没有参数的情况下调用时,TrimLeft删除换行符,空格和tab字符. strming.TrimRight()://消除从 ...

  10. 如何用ModelsimSE仿真IP核-以PLL为例

    我们之前介绍了如何使用Modelsim SE进行仿真和利用do文件的仿真方法,但是其中待仿真的模块是我们自己编写的Verilog模块,但是在实际工作中,我们的设计中会经常用到FPGA厂商给我们提供的现 ...