zoukankan      html  css  js  c++  java
  • HDU 1501 Zipper

    问前两个字符串是否能组合成第三个字符串,保持原字符串的顺序。

    看到别人的代码有两种做法:

    1、DFS

    hash数组标记足迹,可以减少重复搜索的次数。

    这个代码太过巧妙,体会体会再体会。。

     1 //#define LOCAL
     2 #include <iostream>
     3 #include <cstdio>
     4 #include <cstring>
     5 using namespace std;
     6 
     7 bool hash[205][205];
     8 char s1[205], s2[205], s3[410];
     9 
    10 bool DFS(int a, int b, int c)
    11 {
    12     if(s3[c] == '')
    13         return true;
    14     if(hash[a][b])
    15         return false;
    16     hash[a][b] = true;
    17     if(s1[a] == s3[c] && DFS(a+1, b, c+1))
    18         return true;
    19     if(s2[b] == s3[c] && DFS(a, b+1, c+1))
    20         return true;
    21     return false;
    22 }
    23 
    24 int main(void)
    25 {
    26     #ifdef LOCAL
    27         freopen("1501in.txt", "r", stdin);
    28     #endif
    29 
    30     int T, kase;
    31     scanf("%d", &T);
    32     for(kase = 1; kase <= T; ++kase)
    33     {
    34         printf("Data set %d: ", kase);
    35         cin >> s1 >> s2 >> s3;
    36         memset(hash, false, sizeof(hash));
    37         if(DFS(0, 0, 0))
    38             printf("yes
    ");
    39         else
    40             printf("no
    ");
    41 
    42     }
    43     return 0;
    44 }
    代码君

    2、DP

    最优子结构分析:如上例,如果A、B可以组成C,那么,C最后一个字母e,必定是 A 或 C 的最后一个字母组成。

    C去除除最后一位,就变成是否可以求出 A-1和B 或者 A与B-1 与 是否可以构成 C-1
     
    状态转移方程:

    用dp[i][j] 表示 表示A前 i 为 和B 前j 位是否可以组成 C的前i+j位        

            dp[i][j]= (dp[i-1][j]&&(a[i]==c[i+j]))||(dp[i][j-1]&&(b[j]==c[i+j]))

     1 //#define LOCAL
     2 #include <iostream>
     3 #include <cstdio>
     4 #include <cstring>
     5 using namespace std;
     6 
     7 bool dp[205][205];
     8 char s1[205], s2[205], s3[410];
     9 
    10 int main(void)
    11 {
    12     #ifdef LOCAL
    13         freopen("1501in.txt", "r", stdin);
    14     #endif
    15 
    16     int T, kase;
    17     scanf("%d", &T);
    18     for(kase = 1; kase <= T; ++kase)
    19     {
    20         printf("Data set %d: ", kase);
    21         cin >> (s1+1) >> (s2+1) >> (s3+1);
    22         int len1, len2, len3;
    23         len1 = strlen(s1+1);
    24         len2 = strlen(s2+1);
    25         len3 = strlen(s3+1);
    26         if(len1 + len2 != len3)
    27         {
    28             printf("no
    ");
    29             continue;
    30         }
    31         memset(dp, false, sizeof(dp));
    32         int i, j;
    33         i = 0;
    34         while(s1[i] == s3[i])    //处理边界
    35             dp[i++][0] = true;
    36         i = 0;
    37         while(s2[i] == s3[i])
    38             dp[0][i++] = true;
    39         for(i = 1; i <= len1; ++i)
    40             for(j = 1; j <= len2; ++j)
    41                 dp[i][j] = ((dp[i-1][j] && s1[i] == s3[i+j])
    42                             || (dp[i][j-1] && s2[j] == s3[i+j]));
    43 
    44 
    45         if(dp[len1][len2])
    46             printf("yes
    ");
    47         else
    48             printf("no
    ");
    49     }
    50     return 0;
    51 }
    代码君
  • 相关阅读:
    tcp/ip网络分层 紫翼龙王
    软件防火墙之iptables/netfilter概念篇(一) 紫翼龙王
    linux cpu负载详解 紫翼龙王
    ThinkInJava4读书笔记之第五章隐藏实施过程
    ThinkInJava4读书笔记之第六章类继承
    工具类sql操作工具类
    python 面向对象
    python 初识
    python 函数,内置函数
    python 正则,os,sys,hashlib模块
  • 原文地址:https://www.cnblogs.com/AOQNRMGYXLMV/p/3881585.html
Copyright © 2011-2022 走看看