解题思路:

  • dpi,jdp_{i,j}表示从下标iji \to j的最小需要补充的符号数,即区间中不匹配的括号数。初始化 dpi,i=1dp_{i,i} = 1 则有状态转移方程dpi,j=dpi+1,j1+match(i,j)02dp_{i,j} = dp_{i+1,j-1} + match(i,j),匹配为0,不匹配为2
  • 枚举k, k=ij1k, \ k = i \to j-1dpi,j=min(dpi,j,dpi,k+dpk+1,j)dp_{i,j} = \min(dp_{i,j},dp_{i,k} + dp_{k+1,j})
  • 输出答案dp0,len1dp_{0,len-1}
#include<bits/stdc++.h>
using namespace std;
int dp[105][105];
string s;
int match(int x, int y){
    return ((s[x] == '[' && s[y] == ']') || (s[x] == '(' && s[y] == ')'))? 0: 2;
}
int main(){
    cin>>s;
    int len = s.size();
    for(int i = 0; i < len; ++i) dp[i][i] = 1;
    for(int ln = 2; ln <= len; ++ln){
        for(int i = 0; i < len; ++i){
            int j = i + ln - 1 ;
            if(j >= len) break;
            dp[i][j] = dp[i+1][j-1] + match(i, j);
            for(int k = i; k < j; ++k){
                dp[i][j] = min(dp[i][j], dp[i][k] + dp[k+1][j]);
            }
        }
    }
    cout<<dp[0][s.size()-1]<<endl;
    return 0;
}