题目描述

小宇从历史书上了解到一个古老的文明。这个文明在各个方面高度发达,交通方面也不例外。 
考古学家已经知道,这个文明在全盛时期有n座城市,编号为1..n。m条道路连接在这些城市之间,每条道路将两个城市连接起来,使得两地的居民可以方便地来往。 
一对城市之间可能存在多条道路。 据史料记载,这个文明的交通网络满足两个奇怪的特征。 
首先,这个文明崇拜数字K,所以对于任何一条道路,设它连接的两个城市分别为u和v,则必定满足1 <=|u - v| <= K。此外,任何一个城市都与恰好偶数条道路相连(0也被认为是偶数)。 
不过,由于时间过于久远,具体的交通网络我们已经无法得知了。 
小宇很好奇这n个城市之间究竟有多少种可能的连接方法,于是她向你求助。  
方法数可能很大,你只需要输出方法数模1000000007后的结果。

100%的数据满足1 <= n <= 30, 0 <= m <= 30, 1 <= K <= 8.

简化版题意:n个点m条边,满足条件:

  1. 每个点的度为偶数。
  2. 每条边连接的顶点u,v编号之差不超过K且没有自环。

求方案数%1000000007后的值。

思路

  挺神的一道状压$DP$题。难点在于状态量的表示。首先我们分析数据范围,发现$K<=8$,那么很显然状态压缩的那一维和K有关,也是我们直接想到状压$DP$的一个原因。

  那么有$f[i][j][s]$表示前$i$个点,连了$j条边,编号为i-k->i$的点的状态为$s$,那么显然$s$表示的是这些点度数的奇偶性。

  然后快乐的开始推。考虑加入一条边的状态转移。然后,就没有然后了。。。。。。(本人做此题也就到此为止了)

  怎么加边?以$i$为一个端点,另一个呢?很显然这个状态不足以满足$DP$转移,我们需要再加一维,表示当前的$i$向哪个点连边。又因为顶点编号之差$<=k$,我们只需要考虑$i向区间[i-k,i-1]$的连边就可以了。那么有$f[i][j][s][l]表示前i个点,连了j条边,[i-k,i]的状态为s,处理当前点i和i-k+l$之间的连边。

  转移不是特别难(这里采用刷表):

  1. $i和i-k+l不连边,有f[i][j][s][l+1]+=f[i][j][s][l]$
  2. $i和i-k+l$连边,有$f[i][j+1][s$ $ \oplus$ $1<<k$ $\oplus$ $1<<l][l]+=f[i][j][s][l]$
  3. 考虑增加一个点,那么必须有:编号为$i-k$的点度数为偶数,$[i-k,i-1]$区间的点和i已经全部转移

  答案就是$f[n][m][0][k]$前$n$个点连接了$m$条边,当且处理的是$n-k+k=n$,即$[n-k,n-1]$全部处理完的情况。

code

#include<bits/stdc++.h>
using namespace std;
const int p=;
const int S=<<;
int f[][][S][];
int n,m,k; int main()
{
scanf("%d%d%d",&n,&m,&k);
f[][][][]=;//初始化,1,2间没有连边也是一种方案
for(int i=;i<=n;i++)
for(int j=;j<=m;j++)
for(int s=;s<(<<k+);s++)//枚举状态
{
for(int l=;l<k;l++)//枚举i-k+l
{
f[i][j][s][l+]+=f[i][j][s][l]%=p;//不连边
if(i-k+l>&&j<m)f[i][j+][s^(<<l)^(<<k)][l]+=f[i][j][s][l]%=p;//连边
}
if(!(s&))f[i+][j][s>>][]+=f[i][j][s][k]%=p;//把i-k删去,加入i+1
}
cout<<f[n][m][][k];
}

奇怪的道路——状压DP的更多相关文章

  1. 【BZOJ3195】[Jxoi2012]奇怪的道路 状压DP

    [BZOJ3195][Jxoi2012]奇怪的道路 Description 小宇从历史书上了解到一个古老的文明.这个文明在各个方面高度发达,交通方面也不例外.考古学家已经知道,这个文明在全盛时期有n座 ...

  2. BZOJ 3195 [Jxoi2012]奇怪的道路 | 状压DP

    传送门 BZOJ 3195 题解 这是一道画风正常的状压DP题. 可以想到,\(dp[i][j][k]\)表示到第\(i\)个点.已经连了\(j\)条边,当前\([i - K, i]\)区间内的点的度 ...

  3. 【BZOJ-3195】奇怪的道路 状压DP (好题!)

    3195: [Jxoi2012]奇怪的道路 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 305  Solved: 184[Submit][Statu ...

  4. bzoj 3195 奇怪的道路 状压dp

    看范围,状压没毛病 但是如果随便连的话给开1<<16,乘上n,m就爆了 所以规定转移时只向回连边 于是想状态数组:f[i][j]表示到i这里i前K位的状态为j(表示奇偶) 发现有条数限制, ...

  5. bzoj3195 [Jxoi2012]奇怪的道路——状压DP

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3195 看到数据范围就应该想到状压呢... 题解(原来是这样):https://www.cnb ...

  6. 【BZOJ 3195 】[Jxoi2012]奇怪的道路 装压dp

    受惯性思维的影响自动把二进制状态认为是连与不连......... 我们这里二进制状态表示的是奇偶,这样的话我们f[i][j][k]表示的就是前i个城市用了j个边他前k个城市的奇偶状态,然后想想怎么转移 ...

  7. 【bzoj3195】【 [Jxoi2012]奇怪的道路】另类压缩的状压dp好题

    (上不了p站我要死了) 啊啊,其实想清楚了还是挺简单的. Description 小宇从历史书上了解到一个古老的文明.这个文明在各个方面高度发达,交通方面也不例外.考古学家已经知道,这个文明在全盛时期 ...

  8. 算法复习——状压dp

    状压dp的核心在于,当我们不能通过表现单一的对象的状态来达到dp的最优子结构和无后效性原则时,我们可能保存多个元素的有关信息··这时候利用2进制的01来表示每个元素相关状态并将其压缩成2进制数就可以达 ...

  9. 状压dp专题复习

    状压dp专题复习 (有些题过于水,我直接跳了) 技巧总结 : 1.矩阵状压上一行的选择情况 \(n * 2^n\) D [BZOJ2734][HNOI2012]集合选数 蒻得不行的我觉得这是一道比较难 ...

随机推荐

  1. pycharm 激活码 2019/12最新福利(3)

    K6IXATEF43-eyJsaWNlbnNlSWQiOiJLNklYQVRFRjQzIiwibGljZW5zZWVOYW1lIjoi5o6I5p2D5Luj55CG5ZWGOiBodHRwOi8va ...

  2. centos8安装图解

    CentOS 8 的新特性 DNF 成为了默认的软件包管理器,同时 yum 仍然是可用的 使用网络管理器(nmcli 和 nmtui)进行网络配置,移除了网络脚本 使用 Podman 进行容器管理 引 ...

  3. ubuntu14.04 安装tensorflow始末

    基于ubuntu14.04 干净的系统一步步遇到的坑记录下来: 怀着平静学习的心情,问题总的能解决的! 1. 首先看了下当前python版本 python --version Python 2.7.6 ...

  4. python入门经典_好资源送不停

    Python入门经典(2K超清_送书) https://study.163.com/course/courseMain.htm?courseId=1006183019&share=2& ...

  5. .net core 3.0 WPF中使用FolderBrowserDialog

    前言 随着.net core 3.0 的发布,WPF 也可以在 core 平台上使用了.当前的 WPF 不支持跨平台,仅能够在 Windows 平台上使用.如果想体验 WPF 跨平台开发,可以访问开源 ...

  6. 基于KVM的SRIOV直通配置及性能测试

    SRIOV介绍.VF直通配置,以及包转发率性能测试 小慢哥的原创文章,欢迎转载 目录 ▪ 1. SRIOV介绍 ▪ 2. 环境说明 ▪ 3. 开启SRIOV ▪ 4. 生成VF ▪ 5. VF直通 ▪ ...

  7. AutoCAD 2019 for mac 非常好用的CAD三维设计绘图软件

    macOS下用什么cad软件?mac在哪下载cad软件? AutoCAD 2019 for mac 是一款非常好用的CAD三维设计绘图软件,可应用三维建模.CAD.渲染.动画.视觉特效和数字图像. A ...

  8. Oracle基于延时的盲注总结

    0x00 前言 oracle注入中可以通过页面响应的状态,这里指的是响应时间,通过这种方式判断SQL是否被执行的方式,便是时间盲注: oracle的时间盲注通常使用DBMS_PIPE.RECEIVE_ ...

  9. ‎Cocos2d-x 学习笔记(15.1) EventDispatcher

    EventDispatcher对监听器进行管理,围绕着监听器工作.可以添加.删除.暂停/恢复监听器.分发事件到监听器. 1. 一些成员 /** 把ListenerID和同ID监听器的容器对应 */ s ...

  10. 01jmeter-beanshell常用代码段

    1.获取时间 import java.util.*; import java.text.SimpleDateFormat; String str1 = (new SimpleDateFormat(&q ...