zoukankan      html  css  js  c++  java
  • 算法笔记--区间dp

    1.石子归并问题

    dp[i][j]表示区间i到j合并所需的最小花费。

    先求出小区间的最小花费,再转移到大的区间。

    转移方程:dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j])

    初始状态:dp[i][i]=0

    模板:

        for(int i=1;i<=n;i++)cin>>a[i],sum[i]=sum[i-1]+a[i]
        for(int l=2;l<=n;l++){
            for(int i=1;i+l-1<=n;i++){
              int j=i+l-1;
              dp[i][j]=INF;
              for(int k=i;k<j;k++){
                dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j]+sum[j]-sum[i-1]);
            }
        }

    2.括号匹配问题

    求最大括号匹配数

    dp[i][j]表示i到j区间的最大括号匹配数

    先求出小区间的最大括号匹配数,再转移到大区间。

    状态转移:

    dp[i][j]=dp[i+1][j-1]+2(s[i]=='('&&s[j]==')'||s[i]=='['&&s[j]==']')

    dp[i][j]=max(dp[i][k]+dp[k+1][j],dp[i][j])(i<=k<j)

    初始状态:dp[i][j]=0

    模板:

            for(int len=2;len<=s.size();len++){
                for(int i=0;i<s.size();i++){
                    int j=i+len-1;
                    if(j<s.size()){
                        if(s[i]=='('&&s[j]==')'||s[i]=='['&&s[j]==']')dp[i][j]=dp[i+1][j-1]+2;
                        for(int k=i;k<j;k++)
                        dp[i][j]=max(dp[i][k]+dp[k+1][j],dp[i][j]);
                    }
                }
            }

    记录路径,括号补全

    用pos[i][j]记录i到j这段区间从哪个位置断开所要消耗的括号最少,然后从断点分开,递归输出答案。

    模板:

    void dfs(int l,int r){
        if(l>r)return ;
        if(l==r){
            if(s[l]=='('||s[l]==')')putchar('('),putchar(')');
            else putchar('['),putchar(']');
        }
        else{
            if(pos[l][r]==-1){
                putchar(s[l]);
                dfs(l+1,r-1);
                putchar(s[r]);
            }
            else{
                dfs(l,pos[l][r]);
                dfs(pos[l][r]+1,r);
            }
        }
    }
    for(int l=2;l<=len;l++){
                for(int i=0;i+l-1<len;i++){
                    int j=i+l-1;
                    if(s[i]=='('&&s[j]==')'||s[i]=='['&&s[j]==']')dp[i][j]=dp[i+1][j-1]+2,pos[i][j]=-1;
                    for(int k=i;k<j;k++){
                        if(dp[i][k]+dp[k+1][j]>=dp[i][j]){
                            dp[i][j]=dp[i][k]+dp[k+1][j];
                            pos[i][j]=k;
                        }
                    }
                }
            }
    dfs(0,len-1);

    参考博客:http://blog.csdn.net/y990041769/article/details/24194605

  • 相关阅读:
    Altium Designer 16 问题解决
    IAR FOR AVR 仿真过程中出现全局变量值不断随意变化的问题
    linux '--stdin'错误 -批量修改密码
    EmWin 字体相关函数
    EmWin 文本显示函数
    Win10下 usart驱动PL2303无法安装的问题
    EmWin 接触---基础函数
    Linux 下 Samba 服务器搭建
    MPLAB X IDE V4.15 创建工程,编译,问题处理
    EF Core MVC
  • 原文地址:https://www.cnblogs.com/widsom/p/8321670.html
Copyright © 2011-2022 走看看