/**
链接:http://acm.hdu.edu.cn/showproblem.php?pid=6333
题意:n个不相同的数取最多为m的取法数;
NTT 多了一个log 好像直接测就T了
赛后了解正解为莫队时 G++;
**********tricks****
a[i].r a[i].1 输入. 分析组合数的l r 与 n m的状态转移关系;
确定初始l r 值;
*/
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int maxn=1e5+5;
const int mod=1e9+7;
ll fac[maxn],inv[maxn];
ll qpow(ll a,ll b){
ll ans=1;
while(b){
if(b&1) ans=ans*a%mod;
b>>=1;
a=a*a%mod;
}
return ans;
}
ll C(int n,int k){ return fac[n]*inv[k]%mod *inv[n-k]%mod;}
void init(){
fac[0]=fac[1]=1;
for(int i=2;i<maxn;++i) fac[i]=i*fac[i-1]%mod;
inv[maxn-1]=qpow(fac[maxn-1],mod-2);
for(int i=maxn-2;i>=0;i--) inv[i]=inv[i+1]*(i+1)%mod;
}
int pos[maxn];
struct node{
int l,r,id;
bool operator <(const node& a) const{
if(pos[l]==pos[a.l]) return r<a.r;
return pos[l]<pos[a.l];
}
}a[maxn];
ll ans[maxn];
int main(){
init();
ll inv2=qpow(2,mod-2);
int m=sqrt(maxn);
int t;scanf("%d",&t);
for(int i=1;i<=t;i++){
scanf("%d %d",&a[i].r,&a[i].l);
pos[i]=(i-1)/m+1;
a[i].id=i;
}
sort(a+1,a+t+1);
ll res=1;
int l=1,r=0;
// m n
for(int i=1;i<=t;i++){
while(r<a[i].r) {
res=(2*res%mod-C(r,l)+mod)%mod;//s(n+1,m)=2*s(n,m)-c(n,m); 由于得保证C(n,m)的n大于等于m 因此这题应该先扩大r的区间
r++;
}
while(l>a[i].l){
res=(res-C(r,l)+mod)%mod;//s(n,m-1)=s(n,m)-c(n,m);
l--;
}
while(l<a[i].l){
res=(res+C(r,l+1))%mod;//s(n,m+1)=s(n,m)+c(n,m+1);
l++;
}
while(r>a[i].r) {
res=((res+C(r-1,l))%mod)*inv2%mod;//s(n-1,m)=1/2*(s(n,m)+c(n-1,m));
r--;
}
ans[a[i].id]=res;
}
for(int i=1;i<=t;i++) printf("%lld\n",ans[i]);
return 0;
}
HDU 6333 Problem B. Harvest of Apples 莫队.....
猜你喜欢
转载自blog.csdn.net/hypHuangYanPing/article/details/81354894
今日推荐
周排行