Cod sursa(job #861718)

Utilizator toranagahVlad Badelita toranagah Data 21 ianuarie 2013 21:01:20
Problema Secventa 5 Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.4 kb
#include <algorithm>
#include <cstdio>
#include <cstring>
#include <deque>
#include <fstream>
#include <iostream>
#include <vector>
#include <utility>
using namespace std;
#define FORIT(it, v)for(typeof((v).begin()) it=(v).begin();it!=(v).end();++it)
const int MAX_N = (1 << 20) + 10;
typedef vector<pair<int, int> >::iterator vit;
typedef unsigned long long uint64;
typedef unsigned int uint32;
ifstream fin("secv5.in");
ofstream fout("secv5.out");

#define MaxChar 100000
#define verf ((++CharB==MaxChar)?( fin.read(Buffer,MaxChar),CharB=0 ):(1))
  
long CharB=MaxChar-1;
char Buffer [ MaxChar ];
  
void cit ( uint32 &a ){
    bool ok=0;
    for ( ; !( (Buffer[ CharB ]>='0' && Buffer[ CharB ]<='9') || ( Buffer[ CharB ] == '-' ) ); verf )
        ;
    if ( Buffer[ CharB ] == '-' ){
        verf;
        ok=1;
    }
    for ( a=0; (Buffer[ CharB ]>='0' && Buffer[ CharB ]<='9'); a*=10,a+=( Buffer[ CharB ]-'0'), verf )
        ;
    if ( ok ){
        a=-a;
    }
}

uint32 N, L, U;
uint32 sir[MAX_N];
int times_found[MAX_N];
uint64 compute_subsets(uint32*, int, int);
void normalize(uint32*);
 
int main() {
    verf;
    cit(N), cit(L), cit(U);
    for (int i = 1; i <= N; ++i) {
        cit(sir[i]);
    }
    normalize(sir);
    uint64 result = compute_subsets(sir, N, U);
    memset(times_found, 0, sizeof(times_found));
    result -= compute_subsets(sir, N, L - 1);
    fout << result;
    return 0;
}

const int MAX_HASH = 100100;
const int MOD = 100069;
struct Hash {
    vector<pair<int, int> > h[MAX_N];
    void erase(vit iter) {
        int pos = iter->first % MOD;
        h[pos].erase(iter);
    }
    void insert(pair<int, int> p) {
        int pos = p.first % MOD;
        h[pos].push_back(p);
    }
    vit find(int val) {
        int pos = val % MOD;
        FORIT (it, h[pos]) {
            if (it->first == val) return it;
        }
        return end();
    }
    vit end() {
        return h[MOD].end();
    }
} hash;

void normalize(uint32* v) { //cu normalizarea lui Craciun :D
	int on = 0;
    for (int i = 1; i <= N; ++i) {
        vit f = hash.find(v[i]);
        int rez = f == hash.end() ? 0 : f->second;
        if (rez == 0) {
            hash.insert(make_pair(v[i], ++on));
            v[i] = on;
        }
        else v[i] = rez;
    }

    // vector<uint32> norm(v + 1, v + N + 1);
	// sort(norm.begin(), norm.end());
	// norm.resize(unique(norm.begin(), norm.end()) - norm.begin());
	// for (uint32 i = 1; i <= N; ++i) {
	// 	v[i] = lower_bound(norm.begin(), norm.end(), v[i]) - norm.begin() + 1;
	// }
}



uint64 compute_subsets(uint32* v, int n, int limit) {
    if (limit == 0) return 0;
    uint64 result = 0;
    deque<int> dq;
    int numValues = 0;
    for (int i = 1; i <= n; ++i) {
        dq.push_back(v[i]);
        int valBack = dq.back();
        if (times_found[valBack] == 0) {
            ++numValues;
            if (numValues > limit) {
                int valFront = dq.front();
                while (times_found[valFront] > 1) {
                    --times_found[valFront];
                    dq.pop_front();
                    if (dq.front() != valFront) {
                        valFront = dq.front();
                    }
                }
                times_found[valFront] = 0;
                dq.pop_front();
                --numValues;
            }
            times_found[valBack] = 1;
        } else {
        	++times_found[valBack];
        }
        result += dq.size();
    }
    return result;
}