1. 程式人生 > >Codeforces Round #497 (Div. 2) D. Pave the Parallelepiped

Codeforces Round #497 (Div. 2) D. Pave the Parallelepiped

連結

大意

給你(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;
}