Pagini recente » Cod sursa (job #1319929) | Cod sursa (job #1666683) | Cod sursa (job #3280039) | Cod sursa (job #788177) | Cod sursa (job #2520918)
#include <fstream>
#include <bits/stdc++.h>
#include<algorithm>
using namespace std;
ifstream in("rucsac.in");
ofstream out("rucsac.out");
struct obiect
{
float greutate;
int valoare;
};
struct nod
{
int nivel, profit, margine;
float greutate;
};
bool cmp(obiect a, obiect b)
{
double r1 = (double)a.valoare / a.greutate;
double r2 = (double)b.valoare / b.greutate;
return r1 > r2;
}
int Margine(nod u, int n, int W, obiect a[])
{
if (u.greutate >= W)
return 0;
int profit_margine = u.profit;
int j = u.nivel + 1;
int total_greutate = u.greutate;
while ((j < n) && (total_greutate + a[j].greutate <= W))
{
total_greutate+= a[j].greutate;
profit_margine+= a[j].valoare;
j++;
}
if (j<n)
profit_margine += (W - total_greutate) * a[j].valoare /a[j].greutate;
return profit_margine;
}
int knapsack(int W, obiect a[], int n)
{
sort(a, a + n, cmp);
queue<nod> Q;
nod u, v;
//nod de inceput
u.nivel = -1;
u.profit = u.greutate = 0;
Q.push(u);
int maxProfit = 0;
while (!Q.empty())
{
u = Q.front();
Q.pop();
// nod de start
if (u.nivel == -1)
v.nivel = 0;
// ultimul nivel
if (u.nivel == n-1)
continue;
// daca nu este ultimul nivel continuam
v.nivel = u.nivel + 1;
v.greutate = u.greutate + a[v.nivel].greutate;
v.profit = u.profit + a[v.nivel].valoare;
// daca greutate<W si profitul este mai mare decat cel precedent actualizez maximul
if (v.greutate <= W && v.profit > maxProfit)
maxProfit = v.profit;
v.margine = Margine(v, n, W, a);
if (v.margine > maxProfit)
Q.push(v);
v.greutate = u.greutate;
v.profit = u.profit;
v.margine = Margine(v, n, W, a);
if (v.margine > maxProfit)
Q.push(v);
}
return maxProfit;
}
int main()
{
int W,n;
in>>n>>W;
obiect a[100];
for(int i=0; i<n; i++)
in>>a[i].greutate>>a[i].valoare;
out<<knapsack(W, a, n);
return 0;
}
/*
6 10
3 7
3 4
1 2
1 9
2 4
1 5
*/