Cod sursa(job #222531)

Utilizator ilincaSorescu Ilinca ilinca Data 23 noiembrie 2008 11:14:28
Problema Barbar Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.98 kb
#include <stdio.h>
#include <string.h>

#define maxr 1005
#define inf 1<<30


struct queue
{
	int l, c;
};

int r, c, st, dr, max, m [maxr] [maxr];
char w [maxr] [maxr];
queue I, O, q [5*maxr*maxr];



void init ()
{
	int i, j, cr=r+1, cc=c+1;
	for (i=0; i<=cr; ++i)
		for (j=0; j<=cc; ++j)
			m [i] [j]=inf;
	memset (w, '*', sizeof (w));
}

void scan ()
{
	int i, j;
	scanf ("%d%d\n", &r, &c);
	init ();
	for (i=1; i<=r; ++i)
		for (j=1; j<=c; ++j)
		{
			scanf ("%c\n", &w [i] [j]);
			if (w [i] [j] != '.')
			{
				if (w [i] [j] == 'D')
				{
					q [++dr].l=i;
					q [dr].c=j;
					m [i] [j]=0;
				}
				else
					if (w [i] [j] == 'I')
					{
						I.l=i;
						I.c=j;
					}
					else
						if (w [i] [j] == 'O')
						{
							O.l=i;
							O.c=j;
						}
			}
		}
}

void bfs_1 ()
{
	int i, x, y, dl []={0, 0, 0, 1, -1}, dc []={0, 1, -1, 0, 0};
	while (st < dr)
	{
		++st;
		for (i=1; i<=4; ++i)
		{
			x=q [st].l+dl [i];
			y=q [st].c+dc [i];
			if ((w [x] [y] != '*') && (m [x] [y] > m [q [st].l] [q [st].c]+1))
			{
				m [x] [y]=m [q [st].l] [q [st].c]+1;
				if (m [x] [y] > max)
					max=m [x] [y];
				q [++dr].l=x;
				q [dr].c=y;
			}
		}
	}
}

int bfs_2 (int k)
{
	int st, dr, x, y, i, dl []={0, 0, 0, 1, -1}, dc []={0, 1, -1, 0, 0};
	char viz [maxr] [maxr];
	if (m [I.l] [I.c] < k)
		return 0;
	memset (viz, 0, sizeof (viz));
	st=0;
	dr=1;
	q [dr]=I;
	viz [I.l] [I.c]=1;
	while (st < dr)
	{
		++st;
		for (i=1; i<=4; ++i)
		{
			x=q [st].l+dl [i];
			y=q [st].c+dc [i];
			if ((m [x] [y] >= k) && (m [x] [y] < inf) && (!viz [x] [y]))
			{
				q [++dr].l=x;
				q [dr].c=y;
				viz [x] [y]=1;
				if ((q [dr].l == O.l) && (q [dr].c == O.c))
					return 1;
			}
		}
	}
	return 0;
}

int bs ()
{
	int s, i;
	for (s=1; s<=max; s<<=1);
	for (i=0; s>0; s>>=1)
		if ((i+s<=max) && (bfs_2 (i+s)))
			i+=s;
	if ((i == 0) && (!bfs_2 (0)))
		return -1;
	return i;
}

int main ()
{
	freopen ("barbar.in", "r", stdin);
	freopen ("barbar.out", "w", stdout);
	scan ();
	bfs_1 ();
	printf ("%d\n", bs ());
	return 0;
}