Cod sursa(job #612980)

Utilizator GavrilaVladGavrila Vlad GavrilaVlad Data 14 septembrie 2011 09:01:30
Problema Lapte Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.43 kb
#include <cstdio>
#include <algorithm>

using namespace std;

#define maxn 110
#define inf 2000000000

int n, l, a[maxn], b[maxn];
int d[maxn][maxn], rec[maxn][maxn];
int sol, sa[maxn], sb[maxn];

int dinamica(int timp)
{
    for(int i=0; i<=n; ++i)
        for(int j=0; j<=l; ++j)
        {
            d[i][j]=-inf;
            rec[i][j]=0;
        }

    d[0][0]=0;

    for(int i=0; i<n; ++i)
        for(int j=0; j<=l; ++j)
            for(int k=0; k*a[i+1]<=timp; ++k)
                if(d[i+1][j+k]<d[i][j]+(timp-k*a[i+1])/b[i+1])
                {
                    d[i+1][j+k]=d[i][j]+(timp-k*a[i+1])/b[i+1];
                    rec[i+1][j+k]=k;
                }

    if(d[n][l]>=l)
        return 1;

    return 0;
}

void reconstituire(int timp)
{
    int poz=l;

    for(int i=n; i; --i)
    {
        sa[i]=rec[i][poz];
        sb[i]=(timp-a[i]*sa[i])/b[i];
        poz-=rec[i][poz];
    }
}

int main()
{
    freopen("lapte.in", "r", stdin);
    freopen("lapte.out", "w", stdout);

    scanf("%d%d", &n, &l);
    for(int i=1; i<=n; ++i)
        scanf("%d%d", &a[i], &b[i]);

    int left=1, right=100, med;

    while(left<=right)
    {
        med=(left+right)/2;
        if(dinamica(med))
        {
            reconstituire(med);
            sol=med;
            right=med-1;
        }
        else
            left=med+1;
    }

    printf("%d\n", sol);
    for(int i=1; i<=n; ++i)
        printf("%d %d\n", sa[i], sb[i]);

    return 0;
}