Pagini recente » Cod sursa (job #99085) | Cod sursa (job #1520167) | Cod sursa (job #1870619) | Cod sursa (job #1284368) | Cod sursa (job #2965699)
#include <bits/stdc++.h>
using namespace std;
ifstream fin("number.in");
ofstream fout("number.out");
template <class obj>
class heap {
private:
struct nod {
obj val;
nod* down, * next;
nod(obj val)
{
this->val = val;
down = next = NULL;
}
};
nod* root;
inline nod* unit(nod* a, nod* b)
{
if (a == NULL)
return b;
if (b == NULL)
return a;
if (!(a->val < b->val))
swap(a, b);
b->next = a->down;
a->down = b;
return a;
}
nod* convert(nod* x)
{
if (x == NULL || x->next == NULL)
return x;
nod* next1 = x->next;
nod* next2 = next1->next;
return unit(unit(x, next1), convert(next2));
}
public:
inline heap()
{
root = NULL;
}
inline void add(obj val)
{
root = unit(root, new nod(val));
}
inline obj top()
{
return root->val;
}
inline bool empty()
{
return root == NULL;
}
inline void pop()
{
root = convert(root->down);
}
};
int d[351];
struct nod {
int x, flow, totalCost;
bool operator < (nod& aux)
{
return d[x] < d[aux.x] || (d[x] == d[aux.x] && flow > aux.flow);
}
};
heap <nod> H;
int src, dest, flow[351][351], cost[351][351], n, m;
int t[351];
int bound, maxi;
vector <int> g[351];
const int inf = 1000000000;
inline bool bfs()
{
for (int i = 1; i <= n; i++)
d[i] = inf;
d[src] = 0;
H.add({ src, inf, 0});
maxi = 0;
while (!H.empty())
{
nod x = H.top();
H.pop();
if (x.x == dest)
{
maxi = x.flow;
continue;
}
for (auto& i : g[x.x])
{
if (!flow[x.x][i] || d[i] < d[x.x] + (x.totalCost + cost[x.x][i] + bound) * min(x.flow, flow[x.x][i]))
continue;
d[i] = d[x.x] + (x.totalCost + cost[x.x][i] + bound) * min(x.flow, flow[x.x][i]);
H.add({ i, min(x.flow, flow[x.x][i]), x.totalCost + cost[x.x][i] + bound });
t[i] = x.x;
}
}
return maxi;
}
int maxFlow()
{
int res = 0;
while (bfs())
{
int a, b;
b = dest;
a = t[dest];
while (b != src)
{
flow[a][b] -= maxi;
flow[b][a] += maxi;
res += cost[a][b] * maxi;
b = a;
a = t[a];
}
}
return res;
}
int main()
{
fin >> n >> m >> src >> dest;
for (int i = 1; i <= m; i++)
{
int x, y, cap, cst;
fin >> x >> y >> cap >> cst;
g[x].push_back(y);
g[y].push_back(x);
flow[x][y] = cap;
cost[x][y] = cost[y][x] = cst;
bound = min(bound, cst);
}
if (bound < 0)
bound *= -1;
else
bound = 0;
fout << maxFlow();
return 0;
}