牛客删括号 动态规划

https://ac.nowcoder.com/acm/problem/21303

题意中文的不说了;

做法,想到动态规划应该不难的,dp的表示

dp[i][j][k]表示A串扫描了前i个和B串扫描了前j个匹配的情况下,A串删除了的‘(’个数与‘)’的差值;

最终答案就是 dp[lena][lenb][0];

if (a[i] == b[j]) dp[i][j][k] |= dp[i - 1][j - 1][k];
if (a[i] == '(' && k > 0) dp[i][j][k] |= dp[i - 1][j][k - 1];
if (a[i] == ')')  dp[i][j][k] |= dp[i - 1][j][k + 1];

转移方程如上,但是错了是怎么回事,加上一个!k就过了,简单说一下吧

首先看这组样列

(()(()))
()()

一看好像是可以的,但不过AC代码运行结果是不可以的,所以我猜测应该是每次只可以删除必须相连的“()”。

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
char a[110],b[110];
int dp[110][110][110];
int main()
{
    ios::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);
    cin>>a+1;
    cin>>b+1;
    int la=strlen(a+1);
    int lb=strlen(b+1);
    dp[0][0][0]=1;
    for(int i=1; i<=la; i++)
    {
        for(int j=1; j<=lb; j++)
        {
            for(int k=0; k<=la; k++)
            {
                if (!k && a[i] == b[j])
                    dp[i][j][k] |= dp[i - 1][j - 1][k];
                if (a[i] == '(' && k > 0)
                    dp[i][j][k] |= dp[i - 1][j][k - 1];
                if (a[i] == ')')
                    dp[i][j][k] |= dp[i - 1][j][k + 1];
                //if(dp[i][j][k])
                    //cout<<i<<" "<<j<<" "<<k<<endl;
            }
        }
    }
    if(dp[la][lb][0]) cout<<"Possible"<<endl;
    else cout<<"Impossible"<<endl;
    return 0;
}
/**
(()(()))
()()
*/

猜你喜欢

转载自blog.csdn.net/KXL5180/article/details/90045628