Cod sursa(job #1830840)

Utilizator preda.andreiPreda Andrei preda.andrei Data 17 decembrie 2016 10:50:26
Problema Hotel Scor 20
Compilator cpp Status done
Runda Arhiva de probleme Marime 2 kb
#include <cmath>
#include <fstream>
#include <vector>

using namespace std;

struct Nod
{
    int cazati;
    int liber_stanga;
    int liber_dreapta;
    int max_liber;
};

using Aint = vector<Nod>;

int Log2(int n)
{
    return log(n) / log(2);
}

void Update(Aint &aint, int poz, int st, int dr, int x, int y, int val)
{
    if (st == dr) {
        aint[poz].cazati = val;
        aint[poz].max_liber = (val == 0) ? 1 : 0;
        aint[poz].liber_stanga = aint[poz].liber_dreapta = (val == 0) ? 1 : 0;
        return;
    }

    int mij = st + (dr - st) / 2;
    if (x <= mij)
        Update(aint, 2 * poz, st, mij, x, y, val);
    if (mij < y)
        Update(aint, 2 * poz + 1, mij + 1, dr, x, y, val);

    aint[poz].cazati = aint[2 * poz].cazati + aint[2 * poz + 1].cazati;

    aint[poz].liber_stanga = aint[2 * poz].liber_stanga;
    if (aint[2 * poz].liber_stanga == mij - st + 1)
        aint[poz].liber_stanga += aint[2 * poz + 1].liber_stanga;

    aint[poz].liber_dreapta = aint[2 * poz + 1].liber_dreapta;
    if (aint[2 * poz + 1].liber_dreapta == dr - mij)
        aint[poz].liber_dreapta += aint[2 * poz].liber_dreapta;

    aint[poz].max_liber = max(aint[2 * poz].max_liber, 
        aint[2 * poz + 1].max_liber);
    aint[poz].max_liber = max(aint[poz].max_liber,
         aint[2 * poz].liber_dreapta + aint[2 * poz + 1].liber_stanga);
}

void InitAint(Aint &aint, int n)
{
    for (int i = 1; i <= n; ++i)
        Update(aint, 1, 1, n, i, i, 0);
}

int main()
{
    ifstream fin("hotel.in");
    ofstream fout("hotel.out");

    int n, p;
    fin >> n >> p;

    int log_n = Log2(n) + 2;
    Aint aint((1 << log_n) + 1, {0, 0, 0, 0});
    InitAint(aint, n);

    while (p--) {
        int c;
        fin >> c;

        if (c == 3) {
            fout << aint[1].max_liber << "\n";
        } else {
            int i, m;
            fin >> i >> m;
            Update(aint, 1, 1, n, i, i + m - 1, (c == 1) ? 1 : 0);
        }
    }

    return 0;
}