Escape preparations (Big Data edition)

Title from JZYZOJ. I find a lot of places do not find the problem, or a very good binary optimization problem of multiple backpack


Description Description

In "Harry Potter and the Deathly Hallows" in, Harry Potter they fled together, there are many things to put inside Hermione's bag, but the limited size of the package, so we can only put important items in it, given the number of this kind of article, volume, value value now, I hope you can calculate how to make the maximum value of the combination backpack, and output this value, Hermione will thank you very much.


Input Format Input Format

The first \ (1 \) line has \ (2 \) integer, the number of kinds of articles \ (n-\) and volume loading backpack \ (V \) .

Second \ (2 \) line to the \ (n + 1 \) lines each \ (3 \) integers, for the first \ (I \) number of species article \ (m \) , Volume \ (W \) , value \ (S \) .


Output Format Output Format

Only contains an integer, the largest sum is the value of goods can get.


Sample input Sample Input

2 10                            
3 4 3
2 2 5

Sample Output Sample Output

13

Notes Hint

For the data of $ 100% $

$ 1 \ and v \ $ 5000

$ 1 \ n \ le $ 5000

$ 1 \ m \ $ 5000 the

$ 1 \ w \ le $ 5000

$ 1 \ le s \ le $ 5000


If the data range is relatively small, then you can direct this question multiple backpack but natural to use a lot of data to binary Optimized

For multiple backpacks, each number enumerated for each item is repeated operations NATURAL

We know \ (. 1 \) , \ (2 \) , \ (. 4 \) , \ (. 8 \) , \ (16 \) , \ (32 ...... \) , \ (n-2 ^ \) may be composed of \ (1 \) to \ (2 ^ {n + 1 } -1 \) to any of a number within the

So we have for a given \ (\ the n-) , his decomposed into \ (2 ^ x \) the number of the remaining number were filled, can be converted into 01 backpacks do

Conversion Code

for(register int i = 1;i <= n;i++)
{
    for(register int j = 1;j <= m[i];j <<= 1)
    {
        tw[++tot] = j*w[i];
        tv[tot] = j*v[i];
        m[i] -= j;
    }
    if(m[i])//补齐剩下的数
    {
        tw[++tot] = m[i]*w[i];
        tv[tot] = m[i]*v[i];
    }
}

Further new array \ (tw, tv \) to open into the original array \ (max (x) \) times


coding

#include <bits/stdc++.h>
using namespace std;

const int N = 5005;
int n,V,tot = 0,v[N] = {},m[N] = {},w[N] = {}, tw[N*20] = {},tv[N*20] = {},f[N] = {};



inline int read()
{
    register int x = 0;
    register char ch = getchar();
    while(ch < '0' || ch > '9') ch = getchar();
    while(ch >= '0' && ch <= '9')
    {
        x = (x<<3) + (x<<1) + ch-'0';
        ch = getchar();
    }
    return x;
}

inline void optimize()
{
    for(register int i = 1;i <= n;i++)
    {
        for(register int j = 1;j <= m[i];j <<= 1)
        {
            tw[++tot] = j*w[i];
            tv[tot] = j*v[i];
            m[i] -= j;
        }
        if(m[i])
        {
            tw[++tot] = m[i]*w[i];
            tv[tot] = m[i]*v[i];
        }
    }
}


int main()
{
    n = read(); V = read();
    for(register int i = 1;i <= n;i++) m[i] = read(), w[i] = read(), v[i] = read();
    
    optimize();
    for(register int i = 1;i <= tot;i++)
    {
        for(register int j = V;j >= tw[i];j--) f[j] = max(f[j],f[j-tw[i]]+tv[i]);
    }
    printf("%d\n",f[V]);
    return 0;
}

Guess you like

Origin www.cnblogs.com/Mark-X/p/11404648.html