Codeforces149D(카운트 구간 dp)
                                            
 2876 단어  dpcodeforces
                    
일련의 규칙을 제시하는 괄호 (괄호는 일치하는 것) 예를 들어 (() ()) 이 괄호의 정확한 일치는 첫 번째와 마지막, 두 번째와 세 번째, 네 번째와 다섯 번째이다.
지금 괄호를 염색하려면 이런 조건을 제시해야 한다. 1. 괄호는 염색하지 않고 파란색으로 염색하고 빨간색으로 염색할 수 있다.
2. 일치하는 괄호는 동시에 염색할 수 없지만 그 중 하나는 반드시 염색해야 한다.
3. 인접한 괄호는 같은 색으로 염색할 수 없으며 색칠을 하지 않아도 된다.
문제 풀이:
기억 최적화의 장점, 어떤 상태에 어떤 상태를 더해야 하는지, 그리고 새로운 검색, 기록.이 문제는 점차적인 추측으로는 쓰기가 매우 어렵다.
상태: dp[i][j][k][t] 왼쪽(i) 오른쪽(j) 구간 괄호가 k이고 t일 때 가장 큰 방안 수입니다.
#include<iostream>
#include<math.h>
#include<stdio.h>
#include<algorithm>
#include<string.h>
#include<vector>
#include<map>
using namespace std;
typedef long long lld;
const int oo=0x3f3f3f3f;
const lld OO=1LL<<61;
const lld MOD=1000000007;
#define eps 1e-6
#define maxn 705
lld dp[maxn][maxn][3][3];
char str[maxn];
int mat[maxn],stack[maxn];
int n;
void Match()
{
    int top=0;
    for(int i=1;i<=n;i++)
    {
        if(str[i]=='(')
            stack[++top]=i;
        else
        {
            mat[i]=stack[top];
            mat[stack[top]]=i;
            --top;
        }
    }
}
void dfs(int i,int j)
{
    if(i+1==j)
    {
        dp[i][j][0][1]=1;
        dp[i][j][1][0]=1;
        dp[i][j][0][2]=1;
        dp[i][j][2][0]=1;
        return ;
    }
    if(mat[i]==j)
    {
        dfs(i+1,j-1);
        for(int l=0;l<3;l++)
        {
            for(int r=0;r<3;r++)
            {
                if(l!=1)
                    dp[i][j][0][1]=(dp[i][j][0][1]+dp[i+1][j-1][l][r]+MOD)%MOD;
                if(r!=1)
                    dp[i][j][1][0]=(dp[i][j][1][0]+dp[i+1][j-1][l][r]+MOD)%MOD;
                if(l!=2)
                    dp[i][j][0][2]=(dp[i][j][0][2]+dp[i+1][j-1][l][r]+MOD)%MOD;
                if(r!=2)
                    dp[i][j][2][0]=(dp[i][j][2][0]+dp[i+1][j-1][l][r]+MOD)%MOD;
            }
        }
    }
    else
    {
        int m=mat[i];
        dfs(i,m);
        dfs(m+1,j);
        for(int l=0;l<3;l++)
        {
            for(int r=0;r<3;r++)
            {
                for(int x=0;x<3;x++)
                {
                    for(int y=0;y<3;y++)
                    {
                        ///            
                        if(x==1&&y==1)continue;
                        if(x==2&&y==2)continue;
                        dp[i][j][l][r]=(dp[i][j][l][r]+(dp[i][m][l][x]*dp[m+1][j][y][r])%MOD+MOD)%MOD;
                    }
                }
            }
        }
    }
}
int main()
{
    while(scanf("%s",str+1)!=EOF)
    {
        n=strlen(str+1);
        memset(dp,0,sizeof dp);
        Match();
        dfs(1,n);
        lld ans=0;
        for(int l=0;l<3;l++)
            for(int r=0;r<3;r++)
                ans=(ans+dp[1][n][l][r]+MOD)%MOD;
        cout<<ans<<endl;
    }
    return 0;
}
/**
(())
(()())
()
*/
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
【경쟁 프로 전형적인 90문】008의 해설(python)의 해설 기사입니다. 해설의 이미지를 봐도 모르는 (이해력이 부족한) 것이 많이 있었으므로, 나중에 다시 풀었을 때에 확인할 수 있도록 정리했습니다. ※순차적으로, 모든 문제의 해설 기사를 들어갈 예정입니다. 문자열...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.