Sunteți pe pagina 1din 3

/*

Magic Flow Solution


O(N^2*M^2).
Un-optimized version (i.e. explicit graph)

Should NOT earn maximum points.


Uses more memory than borland can handle.

by Radu Berinde
*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

char Type[52][52];
short Val[52][52];

int N, M;
int L1, C1, L2, C2;

int Nr;

typedef struct edge


{
unsigned short v;
short c, f;
struct edge *next, *rev;
} edge;

edge * V[52*52*2];
short tata[52*52*2];
edge * tedge[52*52*2];
short coada[52*52*2];
int cl, cr;
int Flow;

#define INF 32666

int bf()
{
edge *e;
int i;
coada[0] = 1;
memset(tata, 0, sizeof(tata));

for (cl = cr = 0; cl <= cr && !tata[2]; cl++)


for (e = V[coada[cl]]; e; e = e->next)
if (e->f < e->c && !tata[e->v])
{
coada[++cr] = e->v;
tata[e->v] = coada[cl];
tedge[e->v] = e;
}
if (!tata[2]) return 0;

for (i = 2; i != 1; i = tata[i])
tedge[i]->f++, tedge[i]->rev->f--;
return 1;
}

void solve()
{
while (bf())
Flow++;
}

void print()
{
int i, j;
FILE *fo = fopen("magic.out", "wt");
fprintf(fo, "%d\n", Flow);
for (i = 1; i <= N; i++)
for (j = 1; j <= M; j++)
if (Type[i][j] == 2 && tata[Val[i][j]] && !tata[Val[i][j]+1])
fprintf(fo, "%d %d\n", i, j);
fclose(fo);
}

void add_edge(int i, int j, int c)


{
edge *e1, *e2;
e1 = (edge *) malloc(sizeof(edge));
e2 = (edge *) malloc(sizeof(edge));
e1->rev = e2, e2->rev = e1;
e1->c = c, e2->c = 0;
e1->f = 0, e2->f = 0;
e1->v = j, e2->v = i;
e1->next = V[i], e2->next = V[j];
V[i] = e1, V[j] = e2;
}

int vi[4] = {0, -1, 0, 1};


int vj[4] = {-1, 0, 1, 0};
#define ni (i + vi[v])
#define nj (j + vj[v])

void create_graph()
{
int i, j, v;
Val[L1][C1] = 1;
Val[L2][C2] = 2;
Nr = 2;

for (i = 1; i <= N; i++)


for (j = 1; j <= M; j++)
if (Type[i][j] > 0)
{
Val[i][j] = Nr+1;
if (Type[i][j] == 2)
add_edge(Nr+1, Nr+2, 1);
Nr += Type[i][j];
}

for (i = 1; i <= N; i++)


for (j = 1; j <= M; j++)
if (Type[i][j] > 0 || Type[i][j] == -1)
{
for (v = 0; v < 4; v++)
if (Val[ni][nj])
add_edge(Val[i][j] + (Type[i][j] == 2), Val[ni][nj], INF);
}
}

void read_data()
{
int i, j;
char c;
FILE *fi = fopen("magic.in", "rt");
fscanf(fi, "%d %d", &N, &M);
for (i = 1; i <= N; i++)
for (j = 1; j <= M; j++)
{
fscanf(fi, " %c", &c);
Type[i][j] = (c != 'x' && c != 'X') + (c == '*');
if (c == 'M') L1 = i, C1 = j, Type[i][j] = -1;
if (c == 'T') L2 = i, C2 = j, Type[i][j] = -2;
}
fclose(fi);
}

int main()
{
read_data();
create_graph();
solve();
print();
return 0;
}

S-ar putea să vă placă și