Cod sursa(job #2309243)

Utilizator MoldooooooooMoldoveanu Stefan Moldoooooooo Data 28 decembrie 2018 18:35:46
Problema Barbar Scor 50
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.7 kb
#include <cstdio>
#include <queue>
#include <cstring>
#define MaxR 1005
#define max(a, b) (a>b?a:b)
#define min(a, b) (a<b?a:b)
using namespace std;
int Map[MaxR][MaxR], R, C, i, j, Left, Right;
char c; int Fq[2*MaxR]; bool Check[MaxR][MaxR];
int Ox[4]={1, 0, -1, 0};
int Oy[4]={0, 1, 0, -1};
struct Pair{
    int x;
    int y;
    bool equals(Pair P){
        if(x==P.x && y==P.y)return true;
        return false;
    }
};
Pair I, O;
queue<Pair> Q;
Pair make_pair(int x, int y);
void CompleteMap();
bool Valid(Pair x);
bool InMap(Pair x, int D);
bool BinarySearch(int D);
int main()
{
    freopen("barbar.in", "r", stdin);
    freopen("barbar.out", "w", stdout);
    scanf("%d%d", &R, &C); fgetc(stdin);
    for(i=1; i<=R; ++i){
    for(j=1; j<=C; ++j){
        scanf("%c", &c);
        if(c=='*')Map[i][j]=-1;
        else if(c=='D'){
            Map[i][j]=-2;
            Q.push(make_pair(i, j));
        }
        else if(c=='I')I=make_pair(i, j);
        else if(c=='O')O=make_pair(i, j);
    }
    fgetc(stdin);
    }
    CompleteMap();
    Left=0; Right=min(Map[I.x][I.y], Map[O.x][O.y]);
    if(BinarySearch(0)==false){printf("-1"); return 0;}
    for(i=1; i<=R; ++i)memset(Check[i], 0, C+1);
    while(true){
        while(!Q.empty())Q.pop();
        int Mid=(Left+Right)/2;
        if(BinarySearch(Mid)==true) {
            if(Fq[Mid]==2){
                printf("%d", Mid);
                return 0;
            }
            Left=Mid;}
        else Right=Mid;
        for(i=1; i<=R; ++i)memset(Check[i], 0, C+1);
    }
    return 0;
}
Pair make_pair(int x, int y){
    Pair a; a.x=x; a.y=y;
    return a;
}
void CompleteMap(){
    while(!Q.empty()){
        Pair q=Q.front();
        Q.pop();
        for(int k=0; k<4; ++k){
            Pair x=make_pair(q.x+Ox[k], q.y+Oy[k]);
            if(Valid(x)==true){
                Map[x.x][x.y]=max(Map[q.x][q.y], 0)+1;
                Q.push(x);
            }
        }
    }
    return;
}
bool Valid(Pair x){
    if(x.x>=1 && x.x<=R && x.y>=1 && x.y<=C && Map[x.x][x.y]==0)return true;
    return false;
}
bool BinarySearch(int D){
    ++Fq[D];
    Q.push(I); Check[I.x][I.y]=true;
    while(!Q.empty()){
        Pair q=Q.front(); Q.pop();
        for(int k=0; k<4; ++k){
            Pair x=make_pair(q.x+Ox[k], q.y+Oy[k]);
            if(InMap(x, D)==true){
                if(x.equals(O)) return true;
                Q.push(x);
                Check[x.x][x.y]=true;
            }
        }
    }
    return false;
}
bool InMap(Pair x, int D){
    if(x.x>=1 && x.x<=R && x.y>=1 && x.y<=C && (Map[x.x][x.y]>=D || (Map[x.x][x.y]==-2 && D==0)) && Check[x.x][x.y]==false)return true;
    return false;
}