链接
http://codeforces.com/contest/1008/problem/D
大意
给你(A,B,C)(A,B,C),求无序三元组(a,b,c)(a,b,c)使得a|A,b|B,c|Ca|A,b|B,c|C,一共TT组数据,T,A,B,C≤105
题解:
这个和容斥原理有关,代码很简单,就是想不到方法!!!
#include<cstdio>
#include<cstring>
#include<iostream>
#define N 100009
using namespace std;
typedef long long ll;
int fac[N];
int s[10];
int gcd (int a,int b)
{
if(b==0)
return a;
return gcd(b,a%b);
}
void fac_make()
{
for(int i=1;i<=N;i++)
{
for(int j=i;j<=N;j+=i)
{
fac[j]++;
}
}
}
int ok(int a,int b,int c){
if((a&1) && (b&2) && (c&4))
return 1;
if((a&1) && (c&2) && (b&4))
return 1;
if((b&1) && (a&2) && (c&4))
return 1;
if((b&1) && (c&2) && (a&4))
return 1;
if((c&1) && (a&2) && (b&4))
return 1;
if((c&1) && (b&2) && (a&4))
return 1;
return 0;
}
ll cn(int m,int n)
{
ll s=1;
for(int i=0;i<n;i++)
{
s*=(m-i);
s/=(i+1);
}
return s;
}
int main()
{
int t,a,b,c;
//FILE *fp=fopen("t.txt","r");
int p[15];
memset(fac,0,sizeof(fac));
scanf("%d",&t);
fac_make();
while(t--)
{
// cout<<t<<"****"<<endl;
scanf("%d%d%d",&a,&b,&c);
//cout<<a<<" "<<b<<" "<<c<<endl;
int ab=gcd(a,b);
int bc=gcd(b,c);
int ac=gcd(a,c);
int abc=gcd(ab,c);
s[1]=fac[a]-fac[ab]-fac[ac]+fac[abc];//001
s[2]=fac[b]-fac[ab]-fac[bc]+fac[abc];//010
s[4]=fac[c]-fac[bc]-fac[ac]+fac[abc];//100
s[3]=fac[ab]-fac[abc];//011
s[6]=fac[bc]-fac[abc];//110
s[5]=fac[ac]-fac[abc];//101
s[7]=fac[abc];
/*for(int i=1;i<=7;i++) cout<<s[i]<<" ";
cout<<endl;*/
ll ans=0;
for(int i=1;i<8;i++)
{
for(int j=i;j<8;j++)
{
for(int k=j;k<8;k++)
{
if(ok(i,j,k))
{
ll tp=1;
memset(p,0,sizeof(p));
p[i]++;p[j]++;p[k]++;
//cout<<i<<" "<<j<<" "<<k<<endl;
for(int g=1;g<8;g++)
if(p[g]>0)
{
tp*=cn(s[g]+p[g]-1,p[g]);
//cout<<tp<<endl;
}
if(tp>0)
ans+=tp;
//printf("ans=%lld\n",ans);
}
}
}
}
printf("%lld\n",ans);
}
return 0;
}