洛谷 P1101. 单词方阵 --- dfs

看了他们写的太复杂了 怒其不争还是自己把自己的代码完善了
这个题告诉我们 要自信 别人写的代码根本没有自己的简洁
其实就一个问题
这个题的一个坑点就是单词的朝向必须是一样的 就是单词排列必须是直的 在你找下一个单词的时候 你必须按着原有的朝向去找 也就是搜索方向要固定
P1101-单词方阵-洛谷-计算机科学教育新生态.png

#include <bits/stdc++.h>

using namespace std;

const int N = 110;

char g[N][N];
bool st[N][N];
bool ans[N][N];
string s;
int n;
int dx[8] = {0, 0, 1, -1, 1, -1, 1, -1}, dy[8] = {1, -1, 0, 0, 1, -1, -1, 1};

void dfs(int x, int y, int k, int u)
{
    if (u == s.size() - 1) //当能够查询到最后一个字母 证明字符串与题目给的一样 
    {
        for (int i = 0; i <= u; i ++ ) //将查询成功的字符串每个字母所在位置标记一下 向回查询每个字符串位置 
        {
            int l = x - i * dx[k], r = y - i * dy[k];
            ans[l][r] = true;
        }
        return;
    }

    if (g[x][y] == s[0])
    {
        for (int i = 0; i < 8; i ++ )
        {
            int l = x + dx[i], r = y + dy[i];
            if (l > 0 && l <= n && r > 0 && r <= n) //这个题不需要加st[l][r]判断该点有没有使用过 因为最终我们会沿着dx[i]dy[i]的方向一直搜下去 
            {
                if (g[l][r] == s[u + 1])
                {
                    //cout <<i<<  endl;
                    dfs(l, r, i, u + 1);                
                }
            }
        }
    }
    else
    {
        int l = x + dx[k], r = y + dy[k];
        if (l > 0 && l <= n && r > 0 && r<= n && !st[l][r])
            {
                if (g[l][r] == s[u + 1])
                {
                    //cout <<k<<u <<  endl;
                    //st[l][r] = true;
                    dfs(l, r, k, u + 1);
                    //st[l][r] = false;
                }
                else return;
            }
    }
}

void solve()
{
    scanf("%d", &n);
    s = "yizhong";
    for (int i = 1; i <= n; i ++ )
    {
        for (int j = 1; j <= n; j ++ )
        {
            cin >> g[i][j]; 
        }
    }


    for (int i = 1; i <= n; i ++ )
    {
        for (int j = 1; j <= n; j ++ )
        {
            if (g[i][j] == s[0]) //找跟字符串首字母相同的点开始搜 
            {
                dfs(i, j, 0, 0);
            }
        }
    }
    for (int i = 1; i <= n; i ++ )
    {
        for (int j = 1; j <= n; j ++ )
        {
            if (ans[i][j])  //如果被标记了就是答案 
                cout << g[i][j];
            else printf("*");
        }
        cout << endl;
    }
}

int main()
{
    solve();

    return 0;
}
posted @ 2024-04-16 15:53  MsEEi  阅读(24)  评论(0)    收藏  举报