插头dp?你说的是这个吗?

好吧显然不是......

所谓插头dp,实际上是“基于连通性的状态压缩dp”的简称,最先出现在cdq的论文里面

本篇博客致力于通过几道小小的例题(大部分都比较浅显)来介绍一下这种思路清奇的dp是怎么回事

Part I 定义

何为插头?

插头实际上是一个代称,代指两个格之间的连通性

若dp的某一个状态中,有某相邻的两个格子是联通的(比如说处在同一条路径上、被同一个矩形覆盖blablabla),我们就认为这两个格子之间有插头

举个栗子,格子(1,1)和格子(2,1)联通,那么格子(1,1)就有一个下插头,而格子(2,1)有一个上插头,如下图所示

每一个格子可以有的插头数量随着题目而变

对于一道用路径覆盖棋盘的题目(不相交不重叠的路径)而言,每个格子最多有两个插头:这种情况下表示有一条路径从这个格子的某一个插头的那个方向进来,又从另一个插头的那个方向出去了

例如一条回路的插头表示:

何为轮廓线?

轮廓线就是一条分割线,分隔了dp已经覆盖的状态和暂未覆盖的状态,它是在插头dp的棋盘模型中被定义的

插头dp有两种dp方式:逐行递推和逐格递推,其中逐行递推因为在很多题目中状态过多被弃用

当然也不是说逐行递推就没有用了, 但是本文主要讲逐格递推

逐格递推中,轮廓线是这样的:设当前正在递推的格子是(i,j)

那么轮廓线就是一条从棋盘左边界开始,沿着第i行的格子底部向右延伸至格子(i,j)的左下角,然后向上一格,再一直向右延伸到棋盘右边界

轮廓线的长度是m+1,其中m是列数

对于插头dp的棋盘模型,轮廓线上的不同插头状态就是dp的状态,因此可以引出插头dp棋盘模型的状态定义:

定义$dp\left[i\right]\left[j\right]\left[S\right]$表示如下条件时,插头dp的状态:

当前逐格递推到了第$i$行第$j$列的格子,轮廓线上方的插头状态为$S$,其中$S$的是状态压缩的

轮廓线的一个例子如下图:

其中黄色格子是当前正在递推(也就是正在从黄色格子左边的那个格子往黄色格子转移)的格子,红色的就是轮廓线

轮廓线的上方有m个下插头位置和一个右插头位置

PART II 棋盘模型

棋盘模型是插头dp的最常见(前几年最喜欢考)的方法

大概考法就是给你一个比较小的棋盘(15*15左右?或者更大一点),上面可能有些格子是障碍,然后让你用一些闭合路径啊,哈密顿回路啊或者一些奇奇怪怪的形状来覆盖棋盘上的每一个格子

还有一种考法就是给每个格子赋一个权值,然后让你找一条最优的回路或者路径或者某特定形状之类的

这一类题目有一个关键点:把轮廓线画出来以后,轮廓线上方的会是一些完备的“题目要求的形状”和一些“一头扎到”轮廓线下面,也就是被轮廓线切割的形状,而这些被切割的形状在轮廓线上方的分布我们不清楚,但是我们可以用轮廓线上插头的状态来表示所有情形的和

举个例子,现在有一条轮廓线,轮廓线上面有一些插头。我们现在可能不知道轮廓线上面的情况具体是怎么样的,但是我们根据这些插头就能往下推下面的状态

所以我们只要记录这种插头状态下轮廓线上方的答案,然后往下推就好了

也就是说我们把一个需要dfs找覆盖的问题转化成了一个dp模型~

现在的问题就是,我们怎么表示轮廓线上方的插头的状态呢?

cdq在论文中为我们提供了一个比较好的通解——最小表示法

最小表示法是这样的:对于一类插头可以互相配对的dp问题,我们有以下结论:

设从左到右的四个插头a,b,c,d,其中ac配对bd配对,而ab不配对:这种情况不可能存在

因此此时一定要么ab配对cd配对,要么ad配对bc配对

最小表示法,就是从左到右扫一遍所有插头,并这样操作:

如果这个插头已经被标记过了,就跳过

如果没有,设当前的插头是第i个未标记的插头

将所有当前插头联通的插头标记为i,然后进入下一个插头

这养的方法,由于插头dp本身是基于连通性的,所以一定可行,但是缺点是其时间效率可能较低

因此,对于每一道题,我们在确定最小表示法可以的前提下,可以再多加探索一些别的方法

比如下面这道例题:URAL1519

这道题利用的就是括号序列

又比如这道题:BZOJ2331

这道题利用L形自身的性质定义了插头(我甚至都不确定这道题最小表示法能不能用)

棋盘模型的例题很多,这里列举一些供大家参考

HNOI2007 神奇游乐园

HNOI2004 邮递员

HDU1693 eat the trees

POJ1739 Tony's tour

ZJOI2009 多米诺骨牌 (这个准确来说不是插头dp,但是如果只有要求跨越每一行的话可以插头解决)

这些题目的写法基本都是大同小易,都是共同的,很多题甚至可以用同一份代码过掉

但是一定要多写,因为这样才能让插头dp真正熟记于心,同时处理不同的题目也能加深理解

PART III 直线模型

先鸽着......还没学透

例题:NOI2007生成树计数,GDKOI2018d1t4(大概?)

终于!终于!时隔八个月!博主终于打破了咕咕咕的记录!我把NOI2007生成树计数做了!

然后发现其实能讲的不多......

基础原理

我们知道,插头dp的本质,是“基于连通性的状态压缩dp”

那么对于一类构造图/回路/生成树的题目,我们就可以以对一部分点或者边的连通性的描述作为dp的状态,然后进行转移

举个栗子:NOI2007生成树计数

这道题目利用了给定的图的边的特性,推出了一个状态树比较少的dp,然后套进了矩阵快速幂里面做完。

注意这道题目同样利用了最小表示法,又根据第二类斯特林数的理论得到总的状态数很少

方法特性&&注意事项

这个模型的题目,代码复杂度和讨论复杂度和棋盘模型比起来会少很多,但是它的难点不在于这里

这个模型的难点在于构造出符合“无后效性”“状态不重复不遗漏”的dp状态

同时,要注意到“轮廓线”的概念依然存在于直线模型中,只是它的存在被编辑成了其它的形式,例如上一道例题中的

最后,一定要熟记最小表示法的应用

PART IV 总结

插头dp平时可以见到的题目比较少,但是这并不妨碍插头dp成为众多优秀的dp模型中最具有思维复杂度以及讨论的美感的dp之一

考试中遇到插头dp的概率不大

如果遇到了棋盘模型请谨慎开题,避免全场刚一道导致爆炸;

如果遇到了直线模型,请......结合具体问题分析吧【因为实在是变数很多】

最后,不要学习我把一个知识点咕咕咕了长达八个月的时间>_<

省选算法学习-插头dp的更多相关文章

  1. 省选算法学习-dp优化-四边形不等式

    嗯......四边形不等式的确长得像个四边形[雾] 我们在dp中,经常见到这样一类状态以及转移方程: 设$dp\left[i\right]\left[j\right]$表示闭区间$\left[i,j\ ...

  2. 省选算法学习-数据结构-splay

    于是乎,在丧心病狂的noip2017结束之后,我们很快就要迎来更加丧心病狂的省选了-_-|| 所以从写完上一篇博客开始到现在我一直深陷数据结构和网络流的漩涡不能自拔 今天终于想起来写博客(只是懒吧.. ...

  3. 省选算法学习-回文自动机 && 回文树

    前置知识 首先你得会manacher,并理解manacher为什么是对的(不用理解为什么它是$O(n)$,这个大概记住就好了,不过理解了更方便做$PAM$的题) 什么是回文自动机? 回文自动机(Pal ...

  4. 省选算法学习-BSGS与exBSGS与二次剩余

    前置知识 扩展欧几里得,快速幂 都是很基础的东西 扩展欧几里得 说实话这个东西我学了好几遍都没有懂,最近终于搞明白,可以考场现推了,故放到这里来加深印象 翡蜀定理 方程$ax+by=gcd(a,b)$ ...

  5. [入门向选讲] 插头DP:从零概念到入门 (例题:HDU1693 COGS1283 BZOJ2310 BZOJ2331)

    转载请注明原文地址:http://www.cnblogs.com/LadyLex/p/7326874.html 最近搞了一下插头DP的基础知识……这真的是一种很锻炼人的题型…… 每一道题的状态都不一样 ...

  6. 插头DP学习笔记——从入门到……????

    我们今天来学习插头DP??? BZOJ 2595:[Wc2008]游览计划 Input 第一行有两个整数,N和 M,描述方块的数目. 接下来 N行, 每行有 M 个非负整数, 如果该整数为 0, 则该 ...

  7. 模板:插头dp

    前言: 严格来讲有关dp的都不应该叫做模板,因为dp太活了,但是一是为了整理插头dp的知识,二是插头dp有良好的套路性,所以姑且还叫做模板吧. 这里先推荐一波CDQ的论文和这篇博客http://www ...

  8. 【BZOJ】2331: [SCOI2011]地板 插头DP

    [题意]给定n*m的地板,有一些障碍格,要求用L型的方块不重不漏填满的方案数.L型方块是从一个方格向任意两个相邻方向延伸的方块,不能不延伸.n*m<=100. [算法]插头DP [题解]状态0表 ...

  9. URAL1519 Formula 1 —— 插头DP

    题目链接:https://vjudge.net/problem/URAL-1519 1519. Formula 1 Time limit: 1.0 secondMemory limit: 64 MB ...

随机推荐

  1. 手机上如何远程控制Linux服务器?

    这里介绍3个手机软件,分别是JuiceSSH.Termius和Termux,这3个软件都可以实现远程控制Linux服务器(相当于手机SSH客户端),而且使用起来都非常方便,下面我简单介绍一下这3个软件 ...

  2. fold - 折叠输入行, 使其适合指定的宽度

    总览 (SYNOPSIS) ../src/fold [OPTION]... [FILE]... 描述 (DESCRIPTION) 折叠(wrap) 每个 文件 FILE 中 的 输入行 (缺省为 标准 ...

  3. spring mvc + swagger 配置

    首先,添加mvc框架(略)以及Swagger Maven依赖: <dependency> <groupId>io.springfox</groupId> <a ...

  4. 操作文件 -------JavaScrip

    本文摘要:http://www.liaoxuefeng.com/ 在HTML表单中,可以上传文件的唯一控件就是<input type="file">. 注意:当一个表单 ...

  5. MySQL 5.6常用参数配置及说明

    [client] user = root password = Yong_110 [mysql] prompt = [\\u@\\p][\\d]>\\_ no-auto-rehash [mysq ...

  6. 九、Linux 磁盘管理

    Linux 磁盘管理 Linux磁盘管理好坏直接关系到整个系统的性能问题. Linux磁盘管理常用三个命令为df.du和fdisk. df:列出文件系统的整体磁盘使用量 du:检查磁盘空间使用量 fd ...

  7. JZOJ 5812. 【NOIP提高A组模拟2018.8.14】 区间

    5812. [NOIP提高A组模拟2018.8.14] 区间 (File IO): input:range.in output:range.out Time Limits: 1000 ms  Memo ...

  8. Birthday Paradox

    Birthday Paradox Sometimes some mathematical results are hard to believe. One of the common problems ...

  9. Python登录人人网并抓取新鲜事

    from sgmllib import SGMLParser import sys,urllib2,urllib,cookielib class spider(SGMLParser):     def ...

  10. Linux下 导入导出数据库

    1.怎么找到mysql下的bin? 1.1首先我在网上百度了一些Linux下如何导入导出数据.基本都是用mysqldump命令,但是如果没有到指定目录 下,执行这个命令是没有用的.一开始我还以为要在m ...