Nu aveti permisiuni pentru a descarca fisierul grader_test14.in

Cod sursa(job #2066485)

Utilizator alexpetrescuAlexandru Petrescu alexpetrescu Data 15 noiembrie 2017 01:39:10
Problema Vanatoare Scor 75
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.99 kb
#include <cstdio>

FILE *fin = fopen("vanatoare.in", "r"), *fout = fopen("vanatoare.out", "w");

#define INF 1000000

#define ll long long

#define MAXN 16

int lim;
struct myc {ll x, y;} v[1 << MAXN];
struct sol {int x, y;} d[1 << MAXN];

void euclid(ll a, ll b, ll &d, ll &x, ll &y) {
    if (b == 0) {
        d = a;
        x = 1;
        y = 0;
        return ;
    }
    ll x0, y0;
    euclid(b, a % b, d, x0, y0);
    x = y0;
    y = x0 - ((a / b) * y0);
}

inline void mod(ll &x, ll y) {
    if (y > 0 && x < 0) {
        ll cnt = (-x + y - 1) / y;
        x += cnt * y;
    } else if (y > 0 && x > 0) x %= y;
}

inline void calc(myc &r, myc a, myc b) {
    if (a.x == -1 || b.x == -1) {r.x = -1; return ;}
    if (a.x > b.x) {
        myc aux = a;
        a = b;
        b = aux;
    }
    ll t1, t2, d;
    euclid(a.y, b.y, d, t1, t2);
    if (d == 0) {r.x = -1; return ;}
    if ((b.x - a.x) % d) {r.x = -1; return ;}
    r.y = a.y / d * b.y;
    mod(t1, b.y / d);
    r.x = a.x + (b.x - a.x) / d * t1 * a.y;
    mod(r.x, r.y);
    if (r.x > lim || r.x < 0)
        r.x = -1;
}

int main() {
    int n;
    fscanf(fin, "%d%d", &n, &lim);

    for (int i = 0; i < n; i++)
        fscanf(fin, "%lld%lld", &v[1 << (n - i - 1)].x, &v[1 << (n - i - 1)].y);

    for (int i = 1; i < (1 << n); i++) {
        if (i - (i & (-i))) {
            calc(v[i], v[i - (i & (-i))], v[i & (-i)]);
            if (v[i].x == -1) d[i].x = INF;
            else d[i].x = 1;
        } else if (v[i].x <= lim) d[i].x = 1;
        else d[i].x = INF, v[i].x = -1;
        d[i].y = i;
        for (int j = (i - 1) & i; j; j = (j - 1) & i)
            if (v[j].x != -1 && d[j].x + d[i ^ j].x < d[i].x)
                d[i].x = d[j].x + d[i ^ j].x, d[i].y = j;
    }

    int r = (1 << n) - 1;
    fprintf(fout, "%d\n", d[r].x);
    while (r) {
        fprintf(fout, "%lld ", v[d[r].y].x);
        r ^= d[r].y;
    }

    fclose(fin);
    fclose(fout);
    return 0;
}