hdu5072(鞍山regional problem C):容斥,同色三角形模型

现场过的第四多的题。。当时没什么想法,回来学了下容斥,又听学长讲了一讲,终于把它过了

题目大意:
给定n个数,求全部互质或者全部不互质的三元组的个数

先说一下同色三角形模型

n个点 每两个点连一条边(可以为红色或者黑色),求形成的三条边颜色相同的三角形的个数

反面考虑这个问题,只需要c(n,3)减去不同色的三角形个数即可

对于每一个点,所形成的不同色三角形即为 红色边的数量*黑色边的数量,所以可以O(n)地算出不同色三角形的个数(注意总数要除以2)

然后用c(n,3)减一下即可

对于这个题,如果把互质看作红色边,不互质看作黑色边,就可以转化为同色三角形问题了

那如何求 互质的个数和不互质的个数呢

我们可以预处理范围内每个数的倍数的数量,然后对每个数分解质因子,最后容斥一下即可

代码:

#include <iostream>
#include <stdio.h>
#include<string.h>
#include<algorithm>
#include<string>
#include<ctype.h>
using namespace std;
#define MAXN 1000
long long n;
int a[100010];
int prime[100010];
int num[100010];
int isnotprime[100010];
int num_prime=0;
int fac[100010][10];
int np[100010];
long long gcd(long long a,long long b)
{
    return b?gcd(b,a%b):a;
}
long long lcm(long long a,long long b)
{
    return a/gcd(a,b)*b;
}
void setprime()
{
    for(int i = 2 ; i < MAXN ; i ++)
    {
        if(!isnotprime[i])
             prime[num_prime ++]=i;
        for(int j=0;j<num_prime&&i*prime[j]<MAXN;j++)
        {
            isnotprime[i * prime[j]] = 1;
            if(!(i%prime[j] ) )
                break;
        }
    }
    return ;
}
void setfac(int x,int pos)
{
    np[pos]=0;
    for(int i=0;i<num_prime;i++)
    {
        if(!(x%prime[i]))
        {
            fac[pos][np[pos]++]=prime[i];
        }
        while(!(x%prime[i]))
        {
            x/=prime[i];
        }
    }
    if(x>1)
    {
        fac[pos][np[pos]++]=x;
    }
}
long long iae(int pos)
{
    long long res=0;
    for(int i=1;i<(1<<np[pos]);i++)
    {
        long long mut=1,tmp=0;
        for(int j=0;j<np[pos];j++)
        {
            if(i&(1<<j))
            {
                mut*=fac[pos][j];
                tmp++;
            }
        }
        if(tmp&1)
        {
            res+=num[mut]-1;
        }
        else
        {
            res-=num[mut]-1;
        }
    }
    return res;
}
void setnum()
{
    for(int i=2;i<=100000;i++)
    {
        for(int j=i+i;j<=100000;j+=i)
            num[i]+=num[j];
    }
}
int main()
{
    #ifndef ONLINE_JUDGE
        //freopen("in.txt","r",stdin);
    #endif
    int T;
    setprime();
    scanf("%d",&T);
    while(T--)
    {
        memset(num,0,sizeof(num));
        scanf("%I64d",&n);
        for(int i=0;i<n;i++)
        {
            scanf("%d",a+i);
            num[a[i]]++;
            setfac(a[i],i);
        }
        setnum();
        long long ans=0;
        for(int i=0;i<n;i++)
        {
            int tmp=iae(i);
            ans+=(n-1-tmp)*tmp;
        }
        ans=n*(n-1)*(n-2)/6-ans/2;
        printf("%I64d\n",ans);
    }
    return 0;
}
时间: 2024-08-12 12:55:11

hdu5072(鞍山regional problem C):容斥,同色三角形模型的相关文章

BZOJ 2301 [HAOI2011]Problem b (容斥+莫比乌斯反演+分块优化 详解)

2301: [HAOI2011]Problem b Time Limit: 50 Sec  Memory Limit: 256 MB Submit: 2096  Solved: 909 [Submit][Status][Discuss] Description 对于给出的n个询问,每次求有多少个数对(x,y),满足a≤x≤b,c≤y≤d,且gcd(x,y) = k,gcd(x,y)函数为x和y的最大公约数. Input 第一行一个整数n,接下来n行每行五个整数,分别表示a.b.c.d.k Out

hdu4135(容斥,同色三角形模型)

传送门 解答传送门 ac代码(位运算实现容斥原理): #include<bits/stdc++.h> #define per(i,a,b) for(int i=a;i<=b;i++) using namespace std; typedef long long ll; //#define int long long const ll inf =2333333333333333LL; const double eps=1e-8; int read(){ char ch=getchar();

hdu5072 Coprime 2014鞍山现场赛C题 计数+容斥

http://acm.hdu.edu.cn/showproblem.php?pid=5072 Coprime Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others) Total Submission(s): 354    Accepted Submission(s): 154 Problem Description There are n people standing in a

HDU 5072 Coprime (莫比乌斯反演+容斥+同色三角形)

Coprime Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 262144/262144 K (Java/Others) Total Submission(s): 1469    Accepted Submission(s): 579 Problem Description There are n people standing in a line. Each of them has a unique id number. Now

bzoj 2301 Problem b 莫比乌斯反演+容斥

题意:对于给出的n个询问,每次求有多少个数对(x,y),满足a≤x≤b,c≤y≤d,且gcd(x,y) = k,gcd(x,y)函数为x和y的最大公约数 思路:在hdu1695的基础上加上容斥,即:ans=solve(b/k,d/k)-solve((a-1)/k,d/k)-solve((c-1)/k,b/k)+solve((a-1)/k,(c-1)/k),详见代码: /********************************************************* file n

hdu5072 容斥+枚举

这题说的是给了 n 个数字 每个数值大于1 小于100000,n小于100000 ,找出满足下面要求的三人组有多少种 比如abc ( (ab)==(bc)==(ac) ==1 )||( (ab)!=1&&(bc)!=1&&(ac)!=1 ) (()----表示gcd )计算出这样的三元组的个数. 这样考虑 三元组必须满足上面的要求 , 那么我们减去不满足的可能情况 abc 计算与 a互质的个数 和与a不互质的个数 得到了b在内的不可行的方案数,然后这样发现会多算一次 如果a

hdu 5072 Coprime(同色三角形+容斥)

pid=5072">http://acm.hdu.edu.cn/showproblem.php?pid=5072 单色三角形模型 现场赛和队友想了3个小时,最后发现想跑偏了.感觉好可惜的一道题,要是知道这个模型....就能够轻松的拿银了啊. . . 题意不再赘述,就是求同色三角形的个数.总的三角形的个数是C(n,3),仅仅需减去不同色的三角形就可以.对于每一个点(数),与它互质的连红边,不互质的连蓝边,那么对于该点不同色三角形个数为蓝边数*红边数/2,由于同一个三角形被计算了两次. 那么同

hdu 5471(状压DP or 容斥)

想了最复杂的思路,用了最纠结的方法,花了最长的时间,蒙了一种规律然后莫名其妙的过了. MD 我也太淼了. 后面想了下用状压好像还是挺好写的,而且复杂度也不高.推出的这个容斥的规律也没完全想透我就CAO. Count the Grid Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 400    Accepted Submission(s)

POJ 3695 Rectangles (矩形并 状压+容斥定理 好题)

Rectangles Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 3730   Accepted: 1082 Description You are developing a software for painting rectangles on the screen. The software supports drawing several rectangles and filling some of them w