| Run ID | 作者 | 问题 | 语言 | 测评结果 | 时间 | 内存 | 代码长度 | 提交时间 |
|---|---|---|---|---|---|---|---|---|
| 91423 | sh25_zhoumy | 不勤劳的图书管理员 | C++ | 通过 | 974 MS | 17484 KB | 2847 | 2026-06-12 15:44:01 |
#include <bits/stdc++.h> #define MAXN 1000000 #define MOD 1000000007 #define int long long using namespace std; int n,m; struct data{ int x,y,z,id,tp; }v[MAXN],tr[MAXN]; inline int read(){ int x=0,f=1; char ch=getchar(); while(ch<'0'||ch>'9'){ if(ch=='-') f=-1; ch=getchar(); } while(ch>='0'&&ch<='9'){ x=(x<<1)+(x<<3)+(ch^48); ch=getchar(); } return x*f; } int a[MAXN],b[MAXN]; int ord[MAXN],ans[MAXN]; bool cmp1(data x,data y){ if (x.id==y.id){ if (x.x==y.x) return x.y<y.y; else return x.x<y.x; } else return x.id<y.id; } bool cmp2(int x,int y){ if (v[x].x==v[y].x){ if (v[x].y==v[y].y) return x<y; else return v[x].y<v[y].y; } else return v[x].x<v[y].x; } inline int lb(int x){ return x&(-x); } void upd(int pos,int x,int y){ for(int i=pos;i<=n;i+=lb(i)) tr[i].z=((tr[i].z+x)%MOD+MOD)%MOD,tr[i].tp+=y; } data ask(int pos){ data res; res.z=res.tp=0; if (!pos) return res; for(int i=pos;i;i-=lb(i)) res.z=(res.z+tr[i].z)%MOD,res.tp+=tr[i].tp; res.z=(res.z+MOD)%MOD; return res; } void solve(int l,int r){//CDQ本体 if(l>=r)return; int mid=(l+r)>>1; solve(l,mid); solve(mid+1,r); int cnt=0; for(int i=l;i<=r;i++) ord[++cnt]=i; sort(ord+1,ord+1+cnt,cmp2);//偷懒直接用的sort,归并应该更快 for(int i=1;i<=cnt;i++){//顺序做一遍,统计位置小但键值大的点的贡献 int x=ord[i]; if (x<=mid) upd(n-v[x].y+1,v[x].z*v[x].tp,v[x].tp); else { data tmp=ask(n-v[x].y); ans[v[x].id]+=v[x].tp*(tmp.tp*v[x].z+tmp.z)%MOD;ans[v[x].id]%=MOD; } } for(int i=1;i<=cnt;i++){ int x=ord[i]; if (x<=mid) upd(n-v[x].y+1,-v[x].z*v[x].tp,-v[x].tp); } for(int i=cnt;i;i--){//倒叙再做一遍 int x=ord[i]; if (x<=mid) upd(v[x].y,v[x].z*v[x].tp,v[x].tp); else { data tmp=ask(v[x].y-1); ans[v[x].id]+=v[x].tp*(tmp.tp*v[x].z+tmp.z)%MOD;ans[v[x].id]%=MOD; } } for(int i=1;i<=cnt;i++){ int x=ord[i]; if (x<=mid) upd(v[x].y,-v[x].z*v[x].tp,-v[x].tp); } } signed main(){ n=read(),m=read(); int tot=0; for(int i=1;i<=n;i++) v[++tot].x=i,a[i]=v[tot].y=read(),b[i]=v[tot].z=read(),v[tot].id=0,v[tot].tp=1; for(int i=1;i<=m;i++){ int x=read(),y=read(); v[++tot].x=x,v[tot].y=a[x],v[tot].z=b[x],v[tot].id=i,v[tot].tp=-1; v[++tot].x=y,v[tot].y=a[y],v[tot].z=b[y],v[tot].id=i,v[tot].tp=-1; swap(a[x],a[y]);swap(b[x],b[y]); v[++tot].x=x,v[tot].y=a[x],v[tot].z=b[x],v[tot].id=i,v[tot].tp=1; v[++tot].x=y,v[tot].y=a[y],v[tot].z=b[y],v[tot].id=i,v[tot].tp=1; } sort(v+1,v+1+tot,cmp1); solve(1,tot); for(int i=1;i<=m;i++){ ans[i]=((ans[i-1]+ans[i])%MOD+MOD)%MOD; printf("%lld\n",ans[i]); } return 0; }