• FZU


    FZU - 2150 链接
    这道题我原本的思路是判断有多少个连通块,然后通过连通块来判断时间的,
    连通块大于2一定不可能烧毁所有的草;连通块等于2的时候,两个人分别放火,取用时最大值;连通块等于一的时候两个人同时处理一篇区域;没有连通块的时候直接输出0。
    但是就是一直wa,我也找不出原因,可能是公式推错了吧。然后就采用以一种非常暴力的方法

    数据量只有10 * 10,直接暴力四重循环来选择两个人放火的初始位置,然后通过bfs,来判断时间。

    //Powered by CK
    #include<iostream>
    #include<cstring>
    #include<algorithm>
    #include<queue>
    using namespace std;
    typedef pair<int, int> PII;
    const int ax[4] = {1, -1, 0, 0};
    const int ay[4] = {0, 0, 1, -1};
    const int INF = 0x3f3f3f3f;
    int n, m, visit[20][20], maze[20][20];
    bool judge(int x, int y) {
        if(x >= 0 && x < n && y >= 0 && y < m && !visit[x][y] && maze[x][y])
            return true;
        return false;
    }
    int solve(int x1, int y1, int x2, int y2) {
        int ans = -1;
        memset(visit, 0, sizeof visit);
        queue<PII> q;
        q.push(make_pair(x1, y1)), q.push(make_pair(x2, y2));//两点入列
        visit[x1][y1] = visit[x2][y2] = 1;
        while(!q.empty()) {
            int l = q.size();
            for(int i = 0; i < l; i++) {//队列中的火开始延申
                PII temp = q.front();
                q.pop();
                for(int j = 0; j < 4; j++) {
                    int tempx = temp.first + ax[j];
                    int tempy = temp.second + ay[j];
                    if(judge(tempx, tempy)) {
                        visit[tempx][tempy] = 1;
                        q.push(make_pair(tempx, tempy));
                    }
                }
            }
            ans++;
        }
        for(int i = 0; i < n; i++)
            for(int j = 0; j < m; j++)
                if(maze[i][j] && !visit[i][j])//如果有草,并且火没有走过这个点,证明失败,返回INF无穷大
                    return INF;
        return ans;
    }
    int main() {
        // freopen("in.txt", "r", stdin);
        ios::sync_with_stdio(false);
        int t, x = 1;
        char c;
        cin >> t;
        while(t--) {
            cout << "Case " << x++ << ": ";
            cin >> n >> m;
            for(int i = 0; i < n; i++)
                for(int j = 0; j < m; j++) {
                    cin >> c;
                    if(c == '.')    maze[i][j] = 0;
                    else    maze[i][j] = 1;
                }
            int ans = INF;
            for(int i = 0; i < n; i++)
                for(int j = 0; j < m; j++)
                    for(int k = 0; k < n; k++)
                        for(int l = 0; l < m; l++)
                            if(maze[i][j] == 1 && maze[k][l] == 1) {//初始放火位置必须是草
                                int now = solve(i, j, k, l);
                                ans = min(ans, now);
                            }
            if(ans == INF)  cout << "-1" << endl;//枚举所有放火点后还是不能点燃所有的草。
            else    cout << ans << endl;
        }
        return 0;
    }
    

    最后放上我wa了无数次的思路代码

    #include<iostream>
    #include<cstring>
    #include<cstdio>
    #include<algorithm>
    #include<cmath>
    using namespace std;
    const int ax[4] = {1, -1, 0, 0};
    const int ay[4] = {0, 0, 1, -1};
    const int N = 20;
    int maze[N][N], num[N * N], cnt, maxn, n, m;
    bool judge(int x, int y) {
        if(x >= 0 && x < n && y >= 0 && y < m && !maze[x][y])
            return true;
        return false;
    }
    void dfs(int x, int y, int step) {
        maxn = max(maxn, step);
        for(int i = 0; i < 4; i++) {
            int tempx = x + ax[i];
            int tempy = y + ay[i];
            if(judge(tempx, tempy)) {
                maze[tempx][tempy] = 1;
                dfs(tempx, tempy, step + 1);
            }
        }
    }
    int main() {
        // freopen("in.txt", "r", stdin);
        char c;
        int t;
        cin >> t;
        int x = 1;
        while(t--) {
            printf("Case %d: ", x++);
            cin >> n >> m;
            for(int i = 0; i < n; i++)
                for(int j = 0; j < m; j++) {
                    cin >> c;
                    if(c == '#')    maze[i][j] = 0;
                    else    maze[i][j] = 1;
                }
            cnt = 0;
            for(int i = 0; i < n; i++)
                for(int j = 0; j < m; j++) {
                    if(maze[i][j] == 0) {
                        maxn = 0;
                        maze[i][j] = 1;
                        dfs(i, j, 0);
                        num[cnt++] = maxn;
                    }
                }
            if(cnt > 2) cout << "-1" << endl;
            else {
                if(cnt == 2)    cout << max(ceil((double)num[0] / 2.0), ceil((double)num[1] / 2.0)) << endl;
                else if(cnt == 1) {
                    num[0] /= 2;
                    cout << ceil((double)num[0] / 2.0) << endl;
                }
                else    cout << "0" << endl;
            }
        }
        return 0;
    }
    
  • 相关阅读:
    013.ES6 -对象字面量增强型写法
    012. ES6
    011. ES6 语法
    10. 9. Vue 计算属性的setter和getter 以及 计算属性的缓存讲解
    4. Spring MVC 数据响应方式
    3. SpringMVC 组件解析
    9. Vue 计算属性
    【洛谷 2984】给巧克力
    【洛谷 1821】捉迷藏 Hide and Seek
    【洛谷 1821】银牛派对Silver Cow Party
  • 原文地址:https://www.cnblogs.com/lifehappy/p/12604372.html
Copyright © 2020-2023  润新知