比赛 2026.4.4 评测结果 WWWWTTTTTT
题目名称 区间 最终得分 0
用户昵称 2_16鸡扒拌面 运行时间 31.480 s
代码语言 C++ 内存使用 28.21 MiB
提交时间 2026-04-04 09:12:58
显示代码纯文本
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int MAXN=500010;
const int MOD=666623333;

int n,m;
int l[MAXN],r[MAXN];
vector<int> pos;
int Lmin[MAXN*2],Rmax[MAXN*2];
ll preL[MAXN*2],preR[MAXN*2],preLen[MAXN*2];

ll qpow(ll a,ll b){
	ll res=1;
	while(b){
		if(b&1) res=res*a%MOD;
		a=a*a%MOD;
		b>>=1;
	}
	return res;
}

struct SegTree{
	int mn[MAXN*8],mx[MAXN*8];
	void build(int p,int l,int r){
		if(l==r){
			mn[p]=1e9;
			mx[p]=0;
			return;
		}
		int mid=(l+r)/2;
		build(p*2,l,mid);
		build(p*2+1,mid+1,r);
		mn[p]=1e9;
		mx[p]=0;
	}
	void update(int p,int l,int r,int x,int v){
		if(l==r){
			mn[p]=min(mn[p],v);
			mx[p]=max(mx[p],v);
			return;
		}
		int mid=(l+r)/2;
		if(x<=mid) update(p*2,l,mid,x,v);
		else update(p*2+1,mid+1,r,x,v);
		mn[p]=min(mn[p*2],mn[p*2+1]);
		mx[p]=max(mx[p*2],mx[p*2+1]);
	}
	pair<int,int> query(int p,int l,int r,int ql,int qr){
		if(ql<=l&&r<=qr) return {mn[p],mx[p]};
		int mid=(l+r)/2;
		pair<int,int> res={1e9,0};
		if(ql<=mid){
			auto tmp=query(p*2,l,mid,ql,qr);
			res.first=min(res.first,tmp.first);
			res.second=max(res.second,tmp.second);
		}
		if(qr>mid){
			auto tmp=query(p*2+1,mid+1,r,ql,qr);
			res.first=min(res.first,tmp.first);
			res.second=max(res.second,tmp.second);
		}
		return res;
	}
}seg;

int main(){
	freopen("interval.in","r",stdin);
	freopen("interval.out","w",stdout);
	ios::sync_with_stdio(0);cin.tie(0);
	cin>>n>>m;
	for(int i=1;i<=n;i++){
		cin>>l[i]>>r[i];
		pos.push_back(l[i]);
		pos.push_back(r[i]);
	}
	sort(pos.begin(),pos.end());
	pos.erase(unique(pos.begin(),pos.end()),pos.end());
	int tot=pos.size();
	seg.build(1,1,tot);
	vector<pair<int,int>> ev;
	for(int i=1;i<=n;i++){
		int L=lower_bound(pos.begin(),pos.end(),l[i])-pos.begin()+1;
		int R=lower_bound(pos.begin(),pos.end(),r[i])-pos.begin()+1;
		ev.push_back({L,R});
	}
	for(int i=1;i<=n;i++){
		int L=ev[i-1].first,R=ev[i-1].second;
		seg.update(1,1,tot,L,i);
		seg.update(1,1,tot,R-1,i); 
	}
	for(int i=1;i<tot;i++){
		auto res=seg.query(1,1,tot,i,i);
		Lmin[i]=res.first;
		Rmax[i]=res.second;
		preLen[i]=pos[i]-pos[i-1];
	}
	for(int i=1;i<tot;i++){
		preL[i]=preL[i-1]+Lmin[i]*preLen[i]%MOD;
		preR[i]=preR[i-1]+Rmax[i]*preLen[i]%MOD;
	}
	while(m--){
		int A,B;
		cin>>A>>B;
		ll len=B-A+1;
		ll tot1=len*(len+1)/2%MOD;
		ll sum=0;
		for(int i=1;i<tot;i++){
			if(Lmin[i]==1e9) continue;
			int lx=Lmin[i], rx=Rmax[i];
			ll cnt=0;
			ll all=len*(len+1)/2;
			ll lp=0, rp=0;
			if(lx>A){
				ll left_len=lx-A;
				lp=left_len*(left_len+1)/2;
			}
			if(rx<B){
				ll right_len=B-rx;
				rp=right_len*(right_len+1)/2;
			}
			cnt=(all-lp-rp)%MOD;
			sum=(sum+cnt*preLen[i])%MOD;
		}
		ll ans=sum*qpow(tot1,MOD-2)%MOD;
		cout<<ans<<endl;
	}
	return 0;
}