ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

【kuangbin专题】01——简单搜索

2022-07-02 17:31:29  阅读:191  来源: 互联网

标签:专题 int dfs yy ++ xx 01 dx kuangbin


【kuangbin专题】01——简单搜索

https://www.acwing.com/activity/content/90/
目录:

1. 棋盘问题

普通dfs问题,注意回溯。
dfs问题就是每种方案都try一下,一直莽到头,然后再挨个回头(回溯)

#include <bits/stdc++.h>

using namespace std;
typedef long long ll;
int n, k;
ll cnt, res;
char a[10][10];
bool vis[10];

void dfs (int x) {
    if (res == 0)       {cnt ++; return ;}
    if (x == n + 1)     return ;
    for (int i = 1; i <= n; i ++) {
        if (vis[i] || a[x][i] == '.')  continue;
        vis[i] = true;
        res --;
        dfs (x + 1);
        vis[i] = false;
        res ++;
    }
    dfs (x + 1);
}

int main () {
    while (cin >> n >> k, (n+1)||(k+1)) {
        memset (vis, false, sizeof vis);
        cnt = 0, res = k;
        for (int i = 1; i <= n; i ++)
            for (int j = 1; j <= n; j ++)
                cin >> a[i][j];
        dfs (1);
        cout << cnt << endl;
    }
}

2. 地牢大师

简单bfs,不同的是坐标是3维的,开三维数组即可

#include <bits/stdc++.h>

using namespace std;
const int N = 105;
char a[N][N][N];
int d[N][N][N];
int l, r, c, sx, sy, sz;

int dx[] = {0, 0, 0, 0, -1, 1};
int dy[] = {1, 0, -1, 0, 0, 0};
int dz[] = {0, 1, 0, -1, 0, 0};

struct Node {
    int x, y, z;
};

bool Range (int x, int y, int z) {
    if (x > l || x <= 0 || y > r || y <= 0 || z > c || z <= 0)
        return false;
    return true;
}

void bfs () {
    memset (d, 0x3f, sizeof d);
    queue <Node> q;
    q.push ({sx, sy, sz});
    d[sx][sy][sz] = 0;

    while (!q.empty ()) {
        auto t = q.front ();
        q.pop();
        int x = t.x, y = t.y, z= t.z;

        for (int i = 0; i < 6; i ++) {
            int xx = x + dx[i], yy = y + dy[i], zz = z + dz[i];
            if (!Range (xx, yy, zz) || d[xx][yy][zz] != 0x3f3f3f3f || a[xx][yy][zz] == '#') continue;
            d[xx][yy][zz] = d[x][y][z] + 1;
            q.push ({xx, yy, zz});
            if (a[xx][yy][zz] == 'E') {
                cout << "Escaped in " << d[xx][yy][zz] << " minute(s)." << endl;
                return ;
            }
        }
    }
    cout << "Trapped!" << endl;
}

int main () {
    while (cin >> l >> r >> c, l || r || c) {
        for (int i = 1; i <= l; i ++)
            for (int j = 1; j <= r; j ++)
                for (int k = 1; k <= c; k ++) {
                    cin >> a[i][j][k];
                    if (a[i][j][k] == 'S')  sx =  i, sy = j, sz = k;
                }
                    
        bfs ();

    }

}

3. 抓住那头牛

也是套路化的bfs,把三种操作视为状态,存入dx[]即可

#include <bits/stdc++.h>

using namespace std;
const int N = 1e5 + 5;
int d[N];
int st, ed;

bool Range (int x) {
    if (x < 0 || x > 1e5)   return false;
    return true;
}

void bfs () {
    memset (d, 0x3f, sizeof d);
    d[st] = 0;
    queue <int> q;
    q.push (st);

    while (!q.empty ()) {
        int x = q.front ();
        q.pop();

        int dx[] = {-1, 1, x};
        for (int i = 0; i < 3; i ++) {
            int xx = x + dx[i];
            if (!Range (xx) || d[xx] != 0x3f3f3f3f) continue;
            d[xx] = d[x] + 1;
            q.push (xx);
            if (xx == ed) {
                cout << d[xx] << endl;
                return ;
            }
        }
    }
}

int main () {
    cin >> st >> ed;
    if (st == ed) {
        cout << 0 << endl;
        return 0;
    }
    bfs ();

}


//bfs经典模型

4. 翻转

个人觉得初接触有点难理解
逻辑:枚举每一种方案,第一行只能靠改变自身;然后依次通过后面的来改变前面的,最后check最后一行是否满足条件(满足则记录为一种方案)
。。。感觉还有些抽象,我建议多模拟几遍代码,代入数据在草稿纸上演算。。因为我也看了好多遍的

对了,还涉及一些位运算的知识,记得滚回去复习

#include <bits/stdc++.h>

using namespace std;
typedef pair<int, int> pii;
const int N = 20;
int n, m;
char a[N][N], b[N][N];//备用图(在这上面改动) 原图(不变的)
int ans[N][N], tmp[N][N]; //最终方案 临时方案
int dx[] = {0, 1, 0, -1, 0}, dy[] = {0, 0, 1, 0, -1};

bool Range (int x, int y) {
    if (x < 0 || x >= n || y < 0 || y >= m)
        return false;
    return true;
}

void change (int x, int y) {
    for (int i = 0; i < 5; i ++) {
        int xx = x + dx[i], yy = y + dy[i];
        if (Range (xx, yy))     a[xx][yy] ^= 1;
    }
    tmp[x][y] = 1;
}

void dfs () {
    int cnt = 0x3f3f3f3f;
    for (int _ = 0; _ <  1 << m; _ ++) {
        int step = 0;
        memset (tmp, 0, sizeof tmp); //方案置0
        memcpy (a, b, sizeof b); //backup, a=b

        for (int i = 0; i < m; i ++) {
            if (_ >> i & 1) { //保证字典序最小
                step ++;
                change (0, i);
            }
        }

        for (int i = 1; i < n; i ++)
            for (int j = 0; j < m; j ++) {
                if (a[i-1][j] == '1') { //根据上一行的情况来改变本行
                    step ++;
                    change (i, j);
                }
            }

        bool suc = true;
        for (int i = 0; i < m; i ++) {
            if (a[n-1][i] == '1') {
                suc = false;
                break;
            }
        }

        if (suc && step < cnt) {
            cnt  = step;
            memcpy (ans, tmp, sizeof tmp);
        }
    }

    if (cnt == 0x3f3f3f3f)  cout << "IMPOSSIBLE\n";
    else {
        for (int i = 0; i < n; i ++) {
            for (int j = 0; j < m; j ++)
                cout << ans[i][j] << ' ';
            cout << endl;
        }
    }
}

int main () {
    cin >> n >> m;
    for (int i = 0; i < n; i ++)
        for (int j = 0; j < m; j ++)
            cin >> b[i][j];

    dfs  ();
   
}
//dfs + 记录方案

后面的吃完饭来更。。dfs真是烦死人了!!

标签:专题,int,dfs,yy,++,xx,01,dx,kuangbin
来源: https://www.cnblogs.com/CTing/p/16437990.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有