HDU - 6044

题目链接:HDU - 6044


分治区间,对于当前区间可以分成两边计算。

特判无解的情况。


AC代码:

#pragma comment(linker, /STACK:102400000,102400000)
#pragma GCC optimize("-Ofast","-funroll-all-loops")
#include<bits/stdc++.h>
//#define int long long
using namespace std;
const int N=1e6+10,mod=1e9+7;
inline char nc(){
    static char buf[100000],*p1=buf,*p2=buf;
    return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++;
}
template <class T>
inline bool read(T & x){
    char c=nc();   x=0;
    if(c==EOF)return false;
    for(; c>'9'||c<'0'; c=nc());
    for(; c>='0'&&c<='9'; x=x*10+c-'0',c=nc());
    return true;
}
int n,f[N],inv[N],l[N],ts; map<pair<int,int>,int> mp; 
int qmi(int a,int b=mod-2){
	int res=1;
	while(b){if(b&1) res=1LL*res*a%mod; a=1LL*a*a%mod; b>>=1;}
	return res;
}
inline int C(int n,int m){return 1LL*f[n]*inv[m]%mod*inv[n-m]%mod;}
int dfs(int l,int r){
	if(l>r)	return 1;
	int mid=mp[{l,r}]; if(!mid) return 0;
	return 1LL*dfs(l,mid-1)*dfs(mid+1,r)%mod*C(r-l,mid-l)%mod;
}
void solve(){
	for(int i=1;i<=n;i++)	read(l[i]); mp.clear();
	for(int i=1,r;i<=n;i++)	read(r),mp[{l[i],r}]=i;
	printf("Case #%d: %d\n",++ts,dfs(1,n));
}
signed main(){
	f[0]=1; for(int i=1;i<N;i++) f[i]=1LL*f[i-1]*i%mod;
	inv[N-1]=qmi(f[N-1]); for(int i=N-2;i>=0;i--) inv[i]=1LL*inv[i+1]*(i+1)%mod;
	while(read(n))	solve();
	return 0;
}

猜你喜欢

转载自blog.csdn.net/weixin_43826249/article/details/107728328
hdu