Pagini recente » Cod sursa (job #337319) | Cod sursa (job #1223775) | Cod sursa (job #2378849) | Cod sursa (job #966951) | Cod sursa (job #2017810)
#include <fstream>
#include <string.h>
#include <stdlib.h>
#define nmax 355
#define mmax 12505
#define inf 125050000
using namespace std;
fstream f1("fmcm.in", ios::in);
fstream f2("fmcm.out", ios::out);
int n, m, s, d, ok=1;
int aux[nmax], cap[nmax], cost[nmax][nmax], ca[nmax][nmax], v[mmax*2], viz[nmax], coada[mmax], prim, ultim, k, pred[nmax], poz[nmax];
long int dreal1[nmax], dreal2[nmax], dfictiv[nmax], fmax, nrelh;
struct muchii
{
int x, y;
}muc[mmax];
struct heap
{
int32_t nod, dist;
} h[nmax], vii;
void citire()
{
int x, y, c, i,CA;
f1>>n>>m>>s>>d;
for(i=1; i<=m; i++)
{
f1>>muc[i].x>>muc[i].y>>CA>>c;
aux[muc[i].x]++;
aux[muc[i].y]++;
cost[muc[i].x][muc[i].y]=c;
cost[muc[i].y][muc[i].x]=-c;
ca[muc[i].x][muc[i].y]=CA;
}
cap[1]=1;
for(i=2; i<=n+1; i++)
{
cap[i]=cap[i-1]+aux[i-1];
aux[i-1]=cap[i-1];
}
for(i=1; i<=m; i++)
{
x=muc[i].x;
y=muc[i].y;
v[aux[x]]=y;
aux[x]++;
v[aux[y]]=x;
aux[y]++;
}
}
void initb()
{
for(int i=1; i<=n; i++)
dreal1[i]=inf;
prim=1;
ultim=1;
k=1;
coada[prim]=s;
viz[s]=1;
dreal1[s]=0;
}
void bellman()
{
int nod, vec, i;
while(k!=0)
{
nod=coada[prim];
viz[nod]=0;
prim++;
if(prim> mmax-2) prim=1;
k--;
for(i=cap[nod]; i<cap[nod+1]; i++)
{
vec=v[i];
if((ca[nod][vec]>0)&&(dreal1[vec]> dreal1[nod]+cost[nod][vec]))
{
dreal1[vec]= dreal1[nod]+cost[nod][vec];
pred[vec]=nod;
if(!viz[vec])
{
viz[vec]=1;
ultim++;
if(ultim> mmax-2) ultim=1;
k++;
coada[ultim]=vec;
}
}
}
}
if(dreal1[d]!=inf) ok=1;
else ok=0;
}
void actual()
{
int nod;
long int fmin=inf;
nod=d;
while(pred[nod])
{
if(fmin> ca[pred[nod]][nod]) fmin= ca[pred[nod]][nod];
nod=pred[nod];
}
nod=d;
while(pred[nod])
{
ca[pred[nod]][nod]-=fmin;
ca[nod][pred[nod]]+=fmin;
nod=pred[nod];
}
fmax+=dreal2[d]*fmin;
}
void initd()
{
int32_t i;
h[1].nod=s;
h[1].dist=0;
poz[s]=1;
nrelh=1;
for(i=1; i<=n; i++)
if(i!=s)
{
nrelh++;
h[nrelh].nod=i;
poz[i]=nrelh;
h[nrelh].dist=inf;
}
}
void elimina_varf()
{
h[1]=h[nrelh];
nrelh--;
vii=h[1];
int32_t tata=1, fiu=tata*2;
if((fiu+1<=nrelh)&&(h[fiu+1].dist < h[fiu].dist)) fiu++;
while((fiu<=nrelh)&&(vii.dist> h[fiu].dist))
{
h[tata]=h[fiu];
poz[h[fiu].nod]=tata;
tata=fiu;
fiu*=2;
if((fiu+1<=nrelh)&&(h[fiu+1].dist < h[fiu].dist)) fiu++;
}
h[tata]=vii;
poz[vii.nod]=tata;
}
void coboara_urca(int32_t indice)
{
int32_t tata=indice, fiu=indice*2, mos;
vii=h[indice];
if((fiu+1<=nrelh)&&(h[fiu+1].dist < h[fiu].dist)) fiu++;
while((fiu<=nrelh)&&(vii.dist> h[fiu].dist))
{
h[tata]=h[fiu];
///muti h[fiu] pe pozitia h[tata]
poz[h[fiu].nod]=tata;
tata=fiu;
fiu*=2;
if((fiu+1<=nrelh)&&(h[fiu+1].dist < h[fiu].dist)) fiu++;
}
h[tata]=vii;
mos=tata/2;
////vii memo nodul curent de comparat
while((mos>=1)&&(h[mos].dist>vii.dist))
{
h[tata]=h[mos];
poz[h[mos].nod]=tata;
tata=mos;
mos/=2;
}
h[tata]=vii;
poz[vii.nod]=tata;
}
void dijkstra()
{
int vfmin, i, j, vec;
long int mini;
for(i=1; i<=n; i++)
dfictiv[i]=inf;
dreal2[s]=0;
dfictiv[s]=0;
for(i=1; i<=n; i++)
{
mini=h[1].dist;
vfmin=h[1].nod;
if(mini==inf) break;
for(j=cap[vfmin]; j<cap[vfmin+1]; j++)
if((poz[v[j]]<=nrelh)&&(ca[vfmin][v[j]]>0))
{
vec=v[j];
if(h[poz[vec]].dist > mini +cost[vfmin][vec]+ dreal1[vfmin]-dreal1[vec])
{
pred[vec]=vfmin;
h[poz[vec]].dist = mini +cost[vfmin][vec]+ dreal1[vfmin]-dreal1[vec];
coboara_urca(poz[vec]);
dreal2[vec]=dreal2[vfmin]+cost[vfmin][vec];
}
}
dfictiv[vfmin]=mini;
elimina_varf();
}
memcpy(dreal1, dreal2, sizeof(dreal1));
if(dfictiv[d]==inf) ok=0;
}
int main()
{
citire();
initb();
bellman();
while(ok)
{
initd();
dijkstra();
if(ok) actual();
}
f2<<fmax;
return 0;
}