【题解】洛谷P2448: 无尽的生命
P2448 无尽的生命
这题难的不是逆序对模板,主要是如何处理不会操作的数,我们交换操作的与不操作的数可以分割出区间,每个区间我们都当作一个独立的个体。
这个图就可以划分出以下区间(起始编号,区间个数)(1,1),(2,2),(4,1),(5,1),(6,1),(7,1)
此时我们对查询交换区间进行离散化,对新的区间编号,再进行交换和逆序对操作,注意此时求逆序对个数需要乘上区间个数。
#include<bits/stdc++.h> #define int long long #define re register const int N=1e6+10; const int mod=998244353; using namespace std; int n; int b[N],o=0; int idx[N],idy[N]; int t[N],row[N]; int a[N],id[N]; int tree[N]; int len; int lb(int x){ return x&-x; } void add(int x,int k){ while(x<=len){ tree[x]+=k; x+=lb(x); } } int query(int x){ int sum=0; while(x){ sum+=tree[x]; x-=lb(x); } return sum; } signed main(){ ios::sync_with_stdio(false); cin.tie(nullptr); cin>>n; for(int i=1;i<=n;i++){ int x,y; cin>>x>>y; idx[i]=x; idy[i]=y; b[++o]=x; b[++o]=y; } sort(b+1,b+o+1); int tot=unique(b+1,b+o+1)-b-1; len=0; row[++len]=b[1]; t[len]=1; for(int i=2;i<=tot;i++){ if(b[i]-b[i-1]>1){ row[++len]=b[i-1]+1; t[len]=b[i]-b[i-1]-1; } row[++len]=b[i]; t[len]=1; } for(int i=1;i<=len;i++){ id[i]=i; } for(int i=1;i<=n;i++){ int x=lower_bound(row+1,row+1+len,idx[i])-row; int y=lower_bound(row+1,row+1+len,idy[i])-row; swap(t[x],t[y]); swap(id[x],id[y]); } int ans=0; for(int i=len;i>=1;i--){ ans+=query(id[i]-1)*t[i]; add(id[i],t[i]); } cout<<ans; return 0; }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 写一个简单的SQL生成工具
· AI 智能体引爆开源社区「GitHub 热点速览」