HDU 6170 Two strings 思维 DP

  题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=6170

  题目描述: 两个字符串问是否匹配, '.'可以匹配任意字符, '*'可以使前一个数的出现次数成上一个自然数(0, 1, 2, 3........)

  解题思路: DP, dp(i, j)表示A串匹配到j位, B串匹配到i位两个串是否匹配, 转移方程再代码里有, 参考Jaihk662的博客, 注释在代码中

  代码:

#include <iostream>
#include <cstdio>
#include <string>
#include <vector>
#include <cstring>
#include <iterator>
#include <cmath>
#include <algorithm>
#include <stack>
#include <deque>
#include <map>
#define lson l, m, rt<<1
#define rson m+1, r, rt<<1|1
#define mem0(a) memset(a,0,sizeof(a))
#define meminf(a) memset(a,-0x3f,sizeof(a))
#define fi(n) for(i=0;i<n;i++)
#define fj(m) for(j=0;j<m;j++)
#define sca(x) scanf("%d",&x)
#define ssca(x) scanf("%s",x)
#define scalld(x) scanf("%I64d",&x)
#define print(x) printf("%d\n", x)
#define printlld(x) printf("%I64d\n",x)
#define de printf("=======\n")
#define yes printf("YES\n")
#define no printf("NO\n")
typedef long long ll;
using namespace std;

const int maxn = 2600;
char a[maxn];
char b[maxn];
int dp[maxn][maxn]; // dp[i][j] 表示 b串匹配到了第i个,a串匹配到了第j个时, 是否匹配

int main() {
    int t;
    sca( t );
    while( t-- ) {
        mem0(dp);
        ssca(a+1);
        ssca(b+1);
        int la = (int)strlen(a+1);
        int lb = (int)strlen(b+1);
        dp[0][0] = 1;
        if( b[2] == '*' ) dp[2][0] = 1; //初始化
        for( int i = 1; i <= lb; i++ ) {
            for( int j = 1; j <= la; j++ ) {
                if( b[i] == '.' ) { // 如果当前位是'.'或者相等就直接转移
                    dp[i][j] = max(dp[i][j], dp[i-1][j-1] );
                }
                else if( b[i] != '*' ){
                    if( b[i] == a[j] ) {
                        dp[i][j] = max(dp[i][j], dp[i-1][j-1] );
                    }
                }
                else { //当前是'*'
                    dp[i][j] = max( dp[i-1][j], dp[i-2][j] );
                    if( (dp[i-1][j-1] || dp[i][j-1]) && a[j] == a[j-1] ) { /*如果前一位匹配上一位已经匹配或者本位已经匹配 且a串的前后相邻两个字符相等, 主要解决aaaaaaaaaaaaa 和 a* 的这种情况*/
                        dp[i][j] = max( dp[i][j], max(dp[i-1][j-1], dp[i][j-1]) );
                    }
                }
            }
        }
        if( dp[lb][la] ) {
            printf( "yes\n" );
        }
        else {
            printf( "no\n" );
        }
    }
    return 0;
}
View Code

  思考: 一开始想枚举直接判断了, 结果很快就WA了,越到后面越复杂,  心不细就不要枚举......我没想到这道题也能用DP做, 真的是长见识了, 看来对于DP still have a long way to go  啊...... 感觉暑假快结束了, 自己到底有没有提高呢

 

posted on 2017-08-22 21:52  FriskyPuppy  阅读(128)  评论(0编辑  收藏  举报

导航