Sugar points
Title Description
There are N (the same) candy, M a (different) children. M and N satisfying: 1≤M≤N≤100000 (105).
Requirements:
1. Each child has at least one candy.
2. positive integer X (X> = 2) does not exist, so that the number of candy each child is a multiple X.
3. The remaining candy can not.
Partitioned Total sugar method. 1000000007 answer mode (109 + 7)
Input Format
A first number of behavioral data set: T <= 100000.
Next N rows, each row two positive integer N as shown herein, M.
Output Format
Output T lines, each an integer, for the answer.
Note-taking!
Analysis
The difficulty is not a question a lot of friends :)
regular anti difficult it
we count a multiple of the number of candy each child is X's
clear that X should be a factor of N
so the question becomes the N decomposition of the quality factor
and the inclusion-exclusion what
program number of words is identical to a different set of items into b, the set of non-empty case
Code
#include<bits/stdc++.h>
#define int long long
#define re register
#define in read()
using namespace std;
inline int read(){
char ch;int f=1,res=0;
while((ch=getchar())<'0'||ch>'9') if(ch=='-') f=-1;
while(ch>='0'&&ch<='9'){
res=(res<<1)+(res<<3)+(ch^48);
ch=getchar();
}
return f==1?res:-res;
}
const int N=1e5;
const int P=1e9+7;
typedef long long ll;
int T,n,m;
int fac[N+10],ifac[N+10];
inline ll ksm(ll x,ll b){
ll res=1;
while(b){
if(b&1) res=res*x%P;
x=x*x%P;
b>>=1;
}
return res;
}
int mark[N+10],pri[N+10],tot=0;
void init(){
for(re int i=2;i<=N;++i){
if(!mark[i]) pri[++tot]=i;
for(re int j=1;j<=tot&&i*pri[j]<=N;++j){
mark[i*pri[j]]=1;
if(i%pri[j]==0) break;
}
}
fac[0]=1;
for(re int i=1;i<=N;++i) fac[i]=fac[i-1]*i%P;
ifac[N]=ksm(fac[N],P-2);
for(re int i=N-1;i>=0;--i) ifac[i]=ifac[i+1]*(i+1)%P;
}
int cnt=0,a[N];
void divide(int x){
for(re int i=1;pri[i]*pri[i]<=x&&i<=tot;++i)
if(x%pri[i]==0){
a[++cnt]=pri[i];
while(x%pri[i]==0) x/=pri[i];
}
if(x>1) a[++cnt]=x;
}
ll C(ll x,ll y){
if(y>x) return 0;
return fac[x]*ifac[y]%P*ifac[x-y]%P;
}
bool cmp(const int a,const int b){return a>b;}
ll ans;
void dfs(int pos,int sum,int t){
if(pos>cnt){
int x=n/sum;
if(t) ans=(ans-C(x-1,m-1))%P;
else ans=(ans+C(x-1,m-1))%P;
return;
}
dfs(pos+1,sum*a[pos],t^1);
dfs(pos+1,sum,t);
}
void work(){
cnt=0;
divide(n);
ans=0;
sort(a+1,a+cnt+1,cmp);
dfs(1,1,0);
cout<<((ans%P+P)%P)<<'\n';
}
signed main(){
T=in;
init();
while(T--){
n=in;m=in;
if(n==m) puts("1");
else work();
}
return 0;
}