[简单DP] HDOJ 4323 Magic Number

// 编辑距离的方法可以水过这道题

编辑距离的计算方法即一个不完全的证明见:http://en.wikipedia.org/wiki/Levenshtein_distance

具体如下图:

# include <cstdio>

# include <cstring>



# define LEN 10 + 2

# define N 1500 + 5



int n, m;

char s[LEN];

int len[N];

char dic[N][LEN];



int Abs(int x)

{

    return x>0 ? x:-x;

}



int Min(int x, int y, int z)

{

    int t = x<y ? x:y;

    return t<z ? t:z;

}



int levenshtein(char* s, char* t, int n, int m)

{

    int i, j, d[LEN][LEN];            

    for (i = 0; i <= n; ++i)

        d[i][0] = i;

    for (i = 0; i <= m; ++i)

        d[0][i] = i;

    for (i = 1; i <= n; ++i)

    for (j = 1; j <= m; ++j)

    {

        if (s[i-1]==t[j-1])

            d[i][j] = d[i-1][j-1];

        else

            d[i][j] = Min(d[i-1][j], d[i][j-1], d[i-1][j-1])+1;

    }

    return d[n][m];

}



void solve(void)

{

    int i, j, th, lens, cnt;

    scanf("%d%d", &n, &m);

    for (i = 0; i < n; ++i)

    {

        scanf("%s", dic[i]);

        len[i] = strlen(dic[i]);

    }

    for (i = 0; i < m; ++i)

    {

        cnt = 0;

        scanf("%s%d", s, &th);

        lens = strlen(s);

        for (j = 0; j < n; ++j)

        {

            if (Abs(lens-len[j]) > th) continue;

            if (levenshtein(s, dic[j], lens, len[j]) <= th)

                ++cnt;

        }

        printf("%d\n", cnt);

    }

}



int main()

{

    int T;

    

    scanf("%d", &T);

    for (int i = 0; i < T; ++i)

    {

        printf("Case #%d:\n", i+1);

        solve();

    }

    

    return 0;

}

最优性证明可能比较复杂。

你可能感兴趣的:(number)