zoukankan      html  css  js  c++  java
  • 浅谈动态规划

    浅谈动态规划


    前言

    ​ 本蒟蒻认为,在算法竞赛中,最重要的两个算法就是动态规划和搜索。后者可以暴力骗分,也可通过剪枝或记忆化、迭代加深等优化来解决问题。而前者则可以在非指数级时间复杂度内解决许多抽象而复杂的问题。


    定义

    ​ 动态规划($$DP,Dynamic Programming$$)是求解决策问题最优解的算法。

    ​ 一般来说,动态规划可被拆分成三个部分:状态决策阶段。也有三个基本条件:子问题重叠性无后效性最优子结构性质

    1.状态、决策、阶段:

    ​ 为了降低求解的时间复杂度,动态规划算法把原问题视作若干个重叠子问题的逐层递进,每个子问题都有一个状态,构成整个问题的一个阶段,并通过不同的决策方案向更深层问题转移。

    2.子问题重叠性、无后效性、最优子结构性质

    ​ 动态规划将问题分成了若干个子问题,而这些子问题的解决方案被储存在一个表中,而不是需要时再重复计算(类似于记忆化搜索)。而当一个问题,没有共同的子问题,也就是说,其所有的子问题都需要重新计算(无子问题重叠性),那么动态规划是没有用的。

    ​ 在动态规划中,一个子问题通过决策转移至后续问题,而这个子问题不能被后续问题所影响,这就是无后效性。也就是说,如果将动态规划的状态转移成一张图,那么这张图应该是一张有向无环图,而转移顺序应该是这张图的拓扑序

    ​ 对于一个问题,它可以由多个子问题到达,也就是说,下一阶段的最优解应该能够由前面各阶段子问题的最优解导出,这个条件被称作最优子结构。对于一个问题,其的最优解是由前阶段最优子状态,再与最优转移决策综合而来。


    类别与优化

    ​ 对于动态规划,本蒟蒻把其分为了这几个类别

    ​ 1.线性DP

    ​ 2.区间DP

    ​ 3.树形DP

    ​ 4.状压DP

    ​ 5.计数DP

    ​ 6.数位DP

    ​ 而DP的转移有时需要时空上的优化,如:

    ​ 1.优化状态

    ​ 2.数据结构优化

    ​ 3.单调栈、队列优化

    ​ 4.斜率优化

    ​ 5.四边形不等式

    ​ 6.优化枚举顺序

    ​ 7.倍增优化


    一般步骤

    ​ 1.确定一个无后效性、可高效转移的状态

    ​ 2.确定枚举顺序以及初始值

    ​ 3.确定转移方式

    ​ 4.确定答案由哪些状态得来

    ​ 例:0/1背包问题

    ​ 1.设F[i]为包内体积为i时能获得的最大状态

    ​ 2.先遍历每个物品,又由于每个物品只能选一次,所以枚举体积需要倒序枚举

    ​ 3.F[j]这个状态可以由该物品不选到达,也可以由选择该物品到达,也就是F[j] = max(F[j],F[j-v[i]]+w[i]);

    ​ 4.答案是所有状态的最大值


    总结:

    ​ 动态规划一直是算法竞赛中的重点。著名的算法学家、JDOI滴神——QYB曾说过:''想不出来就想动态规划''

    ​ 动态规划的应用十分广泛,但也需要极强的抽象思想,才能设定出高效的状态与转移方程

    ​ 最后,分享一下我特别喜欢的一句话:

    你的一个又一个阶段是由上天安排的,而你,决定的是在这一阶段可以由上一阶段的哪些状态转移而来。越勤奋,越幸运,并不代表这一次你决策的方向有多么优秀,却代表着现在的这一个状态能够续写多少可能的结果
    ——《动态规划》

  • 相关阅读:
    java常用配置文件头部声明
    Error while launching application Error: spawn ENOMEM 解决
    Maven添加依赖后如何在IDEA中引用
    2017-2018 ACM-ICPC East Central North America Regional Contest (ECNA 2017)部分题解
    最小一乘法的一种数值算法?
    LOJ 6409. 「ICPC World Finals 2018」熊猫保护区
    min-max容斥复习
    BMCH
    大象
    关于高维卷积的一些不成熟的想法
  • 原文地址:https://www.cnblogs.com/Marcelo/p/13972454.html
Copyright © 2011-2022 走看看