题目描述:
アラジンは、強力な魔物を召喚する魔法のランプを取得する前に7つの謎を解決しなければならなかったと述べています。ここでは、最初の謎を懸念しています。
アラジンは、魔法の洞窟に入ることについてだった、アラジンの叔父に変装し邪悪な魔術師が率いる、入り口に奇妙な魔法の飛行カーペットを発見しました。洞窟の入り口を守って、いくつかの奇妙な生き物がいました。アラジンは、実行することができますが、彼は捕まるの高いチャンスがあったことを知っていました。だから、彼は魔法飛んでカーペットを使用することにしました。カーペットは、長方形の形状でしたが、正方形ではありません。アラジンは、カーペットを取り、それの助けを借りて、彼は入り口を通過しました。
今、あなたはカーペットや絨毯の可能な最小辺の長さの面積を与えている、あなたのタスクは、カーペットの多くの種類が可能であり、どのように見つけることです。例えば、カーペット12の面積、及びカーペットの最小の可能な側面が2である場合、カーペットの二種類が存在することができ、それらの側面がある:{2,6}および{3,4}。
输入:
テストケースの数を表す整数T(≤4000)を用いて入力を開始します。
二つの整数を含む行を有する各ケース開始:カーペットの面積を示し、Bは、カーペットの最小の可能な側面を示しAB(1件の≤B≤≤1012)
输出:
各ケースで、ケース番号を印刷し可能なカーペットの数。
输入样例:
2
10 2
122
出力サンプル:
ケース1 :. 1。
ケース2:2
説明タイトル:
Bに等しい整数数割り切れるよりも大きくすることができる記録。
知識:
算術の基本定理。
問題解決のアイデア:
素因数分解定理、最初のユニークな因数分解、正の数の全ての数はNUM =(1 + A1)*についてです * ...(+ aiを1)(1 + A2)、aiはどこインデックス素因数があり、見るだけ分解定理、NUM 2は、重複を削除するような話題をc == dは、少ないし、Bの除数より列挙子は、他NUMを失う取るというケースは存在しませんので、それ
コード:
#include<stdio.h>
#include<string.h>
const int max=1000050;
int prim[1000050],f[1000050];
long long k;
void find()//素数打表
{
k=0;
memset(f,0,sizeof(f));
f[0]=1;f[1]=1;
for(int i=2;i<=max;i++)
{
if(!f[i])
{
prim[k++]=i;//存储素数
for(int j=i*2;j<=max;j+=i)//翻倍递增
f[j]=1;//标记非素数
}
}
}
long long ff(long long a)//求因子个数
{
long long s=1,i=0;
while(prim[i]<a&&i<k)
{
int sum=0;
while(a%prim[i]==0)
{
a=a/prim[i];
sum++;//记录能被整除的次数(次方数)
}
s=s*(sum+1);//根据算法的基本定理叠乘
i++;
}
if(a>1)//当a大于一时,没被整除,说明还有一个素数,sum(次方)=1
s=s*2;
return s;
}
int main()
{
int t,l=0;
find();//素数打表
scanf("%d",&t);
while(t--)
{
l++;
long long a,b,i,j,m,n=0,s;
scanf("%lld %lld",&a,&b);
if(b*b>a)
{
printf("Case %d: 0\n",l);
continue;
}
s=ff(a)/2;
for(i=1;i<b;i++)//暴力枚举
{
if(a%i==0)
s--;
}
printf("Case %d: %lld\n",l,s);
}
return 0;
}