Cod sursa(job #1344937)

Utilizator fluture.godlikeGafton Mihnea Alexandru fluture.godlike Data 17 februarie 2015 09:02:16
Problema Pairs Scor 0
Compilator cpp Status done
Runda prega_rav_1 Marime 1.53 kb
#include <stdio.h>
#define lim 1000023LL
#define NMAX 100023LL
#define i64 long long int
FILE *fin, *fout;
i64 n, val, nr, size, div[NMAX], arr[NMAX], maxim, rez1;
i64 max(i64 a, i64 b)
{
    return (a> b)?a:b;
}
bool check[lim];
void fp(i64 a)
{
    if(a%2 == 0)
    {
        div[size] = 2;
        size++;
        while(a%2 == 0) a/=2;
    }
    for(i64 i = 3; i*i <= a && a> 1; i+=2)
    {
        if(a%i) continue;
        div[size] = i;
        size++;
        while(a%i == 0) a/=i;
    }
    if(a > 1)
    {
        div[size] = a;
        size++;
    }
}
i64 vef()
{
    i64 rez = 1, count = 0;
    for(i64 i = 1; i<= nr; i++) rez *= div[arr[i] - 1];
    for(i64 i = 1; i*rez < lim; i++)
    {
        if(check[i*rez] == 1) count++;
    }
    return count*(count-1)/2;
}
i64 comb(i64 len, i64 pos)
{
    i64 rez = 0;
    if(pos == len+1) return vef();
    for(i64 i = arr[pos-1]+1; i<= size; i++)
    {
        arr[pos] = i;
        rez+= comb(len, pos+1);
    }
    return rez;
}
int main()
{
    fin = freopen("pairs.in", "r", stdin);
    fout = freopen("pairs.out", "w", stdout);
    scanf("%lld", &n);
    rez1 = n*(n-1)/2;
    for(i64 i = 0; i< n; i++)
    {
        scanf("%lld", &val);
        maxim = max(maxim, val);
        check[val] = 1;
        for(i64 j = 0; j< size; j++) while(val%div[j] == 0) val/=div[j];
        fp(val);
    }
    for(i64 i = 1; i<= size; i++)
    {
        nr = i;
        if(i%2) rez1 -= comb(i, 1);
        else rez1 += comb(i, 1);
    }
    printf("%lld\n", rez1);
    fclose(fin);
    fclose(fout);
    return 0;
}