Submission #1021157

#TimeUsernameProblemLanguageResultExecution timeMemory
1021157Alihan_8Virus Experiment (JOI19_virus)C++17
0 / 100
659 ms262144 KiB
#include <bits/stdc++.h>

using namespace std;

#define all(x) x.begin(), x.end()
#define ar array
#define pb push_back
#define ln '\n'
#define int long long

using i64 = long long;

template <class F, class _S>
bool chmin(F &u, const _S &v){
    bool flag = false;
    if ( u > v ){
        u = v; flag |= true;
    }
    return flag;
}

template <class F, class _S>
bool chmax(F &u, const _S &v){
    bool flag = false;
    if ( u < v ){
        u = v; flag |= true;
    }
    return flag;
}

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

signed main(){
    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int m, r, c; cin >> m >> r >> c;

    string d; cin >> d;

    d += d; m *= 2;

    map <char,int> dir = {{'W', 0}, {'N', 1}, {'E', 2}, {'S', 3}};

    vector <vector<int>> a(r, vector <int> (c));

    vector <vector<vector<int>>> way(r, vector <vector<int>> (c));

    vector <set<pair<int,int>>> st(16);

    for ( int i = 0; i < r; i++ ){
        for ( int j = 0; j < c; j++ ){
            cin >> a[i][j];

            chmin(a[i][j], m);

            for ( int k = 0; k < 16; k++ ){
                st[k].insert({a[i][j], i * c + j});
            }
        }
    }
    { // initializing "way"
        vector <int> nxt(4, m);

        for ( int i = m - 1; i >= 0; i-- ){
            nxt[dir[d[i]]] = i;

            vector <ar<int,2>> p_;

            for ( int j = 0; j < 4; j++ ){
                p_.pb({nxt[j], j});
            }

            sort(all(p_));

            p_.pb({m + 1, 5});

            int mask = 0;

            for ( int k = 0; k < 4; k++ ){
                auto [x, j] = p_[k];

                mask |= 1 << j;

                auto &s = st[mask];

                int r = p_[k + 1][0] - i + 1;

                auto it = s.lower_bound({x - i + 1, -1});

                vector <pair<int,int>> er;

                while ( it != s.end() && it -> first < r ){
                    int y = it -> second;

                    way[y / c][y % c].pb(mask);

                    er.pb(*it);

                    it = next(it);
                }

                for ( auto &y: er ){
                    s.erase(y);
                }
            }
        }
    }

    auto ok = [&](int x, int y){
        return x >= 0 && y >= 0 && x < r && y < c;
    };

    auto f = [&](int sx, int sy){
        if ( !a[sx][sy] ){
            return r * c + 1;
        }

        vector <vector<int>> is(r, vector <int> (c));

        is[sx][sy] = true;

        queue <ar<int,2>> q;

        q.push({sx, sy});

        int cnt = 0;

        while ( !q.empty() ){
            auto [u, v] = q.front();
            q.pop();

            cnt++;

            for ( int i = 0; i < 4; i++ ){
                int x = dx[i] + u, y = dy[i] + v;

                if ( !ok(x, y) || !a[x][y] || is[x][y] ){
                    continue;
                }

                bool check = false;

                for ( auto &mask: way[x][y] ){
                    bool flag = true;

                    for ( int j = 0; j < 4; j++ ){
                        if ( mask >> j & 1 ){
                            int tx = dx[j] + x, ty = dy[j] + y;

                            if ( !ok(tx, ty) || !is[tx][ty] ){
                                flag = false;

                                break;
                            }
                        }
                    }

                    check |= flag;
                }

                if ( check > 0 ){
                    is[x][y] = 1;

                    q.push({x, y});
                }
            }
        }

        return cnt;
    };

    if ( count(all(d), 'S') == 0 && count(all(d), 'N') == 0 ){
        vector <int> is(c);

        auto f = [&](int r, int s){
            if ( !a[r][s] ){
                return r * c + 1;
            }

            is.assign(c, 0);

            is[s] = true;

            queue <int> q;

            q.push(s);

            int cnt = 0;

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

                cnt++;

                for ( int i = 0; i < 4; i += 2 ){
                    int v = dy[i] + u;

                    if ( !ok(r, v) || !a[r][v] || is[v] ){
                        continue;
                    }

                    bool check = false;

                    for ( auto &mask: way[r][v] ){
                        bool flag = true;

                        for ( int j = 0; j < 4; j++ ){
                            if ( mask >> j & 1 ){
                                int tx = dx[j] + r, ty = dy[j] + v;

                                if ( !ok(tx, ty) || !is[ty] ){
                                    flag = false;

                                    break;
                                }
                            }
                        }

                        check |= flag;
                    }

                    if ( check > 0 ){
                        is[v] = 1;

                        q.push(v);
                    }
                }
            }

            return cnt;
        };

        int mn = r * c + 1, cnt = 0;

        for ( int i = 0; i < r; i++ ){
            for ( int j = 0; j < c; j++ ){
                int q = f(i, j);

                if ( chmin(mn, q) ){
                    cnt = 1;
                } else if ( mn == q ){
                    cnt++;
                }
            }
        }

        cout << mn << ln << cnt;

        return 0;
    }

    int mn = r * c + 1, cnt = 0;

    for ( int i = 0; i < r; i++ ){
        for ( int j = 0; j < c; j++ ){
            int q = f(i, j);

            if ( chmin(mn, q) ){
                cnt = 1;
            } else if ( mn == q ){
                cnt++;
            }
        }
    }

    cout << mn << ln << cnt;

    cout << '\n';
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...