Cod sursa(job #2287337)

Utilizator ValentinSavoiuFMI Savoiu Valentin-Marian ValentinSavoiu Data 21 noiembrie 2018 19:42:39
Problema Barbar Scor 80
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 3.09 kb
#include <fstream>
#include <queue>
using namespace std;
ifstream f("barbar.in");
ofstream g("barbar.out");
int A[1003][1003], inQ[1003][1003], C[1003][1003];
int N, M, i ,j, ist, jst, ifin, jfin;
int dx[] = {0, 0, -1, 1}, dy[] = {1, -1, 0, 0};
queue <pair <int, int> > Q;
pair <int, int> pe;


void read (int &N, int &M) {
    f >> N >> M;
    char aux [1003];
    f.get();
    for (i = 1; i <= N; i++) {
        f.getline(aux, 1001);
        for(j = 1; j <= M; j++) {
            char ch = aux[j - 1];
            switch (ch) {
                case '.' :
                    A[i][j] = 0;
                    break;
                case '*' :
                    A[i][j] = -1;
                    break;
                case 'I' :
                    A[i][j] = 0;
                    ist = i;
                    jst = j;
                    break;
                case 'O' :
                    A[i][j] = 0;
                    ifin = i;
                    jfin = j;
                    break;
                case 'D' :
                    A[i][j] = -1;
                    Q.push(make_pair(i, j));
                    break;
            }
        }
    }
    for (i = 0; i <= N; i++)
        A[i][0] = A[i][M + 1] = -1;
    for (j = 0; j <= M; j++)
        A[0][j] = A[N + 1][j] = -1;
}


void bfdragon() {
    while (!Q.empty()) {
        pe = Q.front();
        Q.pop();
        i = pe.first;
        j = pe.second;
        for (int k = 0; k < 4; k++) {
            int ii = i + dx[k];
            int jj = j + dy[k];
            if (ii >= 0 && ii <= N && jj >= 0 && jj <= M && C[ii][jj] == 0 ) {
                Q.push(make_pair(ii, jj));
                if ( C[i][j] == -1 ) C[ii][jj] = 1;
                else C[ii][jj] = C[i][j] + 1;
            }
        }
    }
    for (i = 0; i <= N; i++)
        for (j = 0; j <= N; j++)
            if (A[i][j] != -1) A[i][j] = C[i][j];
}

bool BF(int dist) {
    if (A[ist][jst] < dist || A[ifin][jfin] < dist) return false;
    Q.push(make_pair(ist, jst));
    while(!Q.empty()) {
        pe = Q.front();
        i = pe.first;
        j = pe.second;
        Q.pop();
        for (int k = 0; k < 4; k++) {
            int ii = i + dx[k];
            int jj = j + dy[k];
            if (ii == ifin && jj == jfin) {
                while (!Q.empty()) Q.pop();
                return true;
            }
            if (A[ii][jj] >= dist && inQ[ii][jj] != dist) {
                Q.push(make_pair(ii, jj));
                inQ[ii][jj] = dist;
            }
        }
    }
    return false;
}

int binary_search() {
   int left = 1, right = N + M, last_good = 0;
   while (left <= right) {
       int mid = left + (right - left) / 2;
       if (BF(mid)) {
           left = mid + 1;
           last_good = mid;
       }
       else right = mid - 1;
   }
   if (last_good) return last_good;
   else return -1;
}
void print() {
    for (i = 1; i <= N; i++) {
        for (j = 1; j <= M; j++)
            g << A[i][j] << ' ';
        g << '\n';
    }
    g << '\n';
}
int main() {

    read(N, M);
    bfdragon();
    //print();
    int sol = binary_search();
    if (sol) g << sol;
    else g << -1;
    return 0;
}