社区讨论

分块,错在10-15测试点有重复部分,求调。

P1975[国家集训队] 排队参与者 3已保存回复 2

讨论操作

快速查看讨论及其快照的属性,并进行相关操作。

当前回复
2 条
当前快照
1 份
快照标识符
@lo1gik2l
此快照首次捕获于
2023/10/22 20:40
2 年前
此快照最后确认于
2023/11/02 21:04
2 年前
查看原帖
错误应该是在有重复 hh 部分,
但是我检查过我的程序重复部分都应该判了的,
不知道为什么还是错。
CPP
#include<bits/stdc++.h>
using namespace std;
const int N = 5e5 + 10, W = 2200, C = 230;
int n, Q, c, l, r, lc, rc;
int a[N];
long long cnt = 0, cnt2 = 0;
int tr[2 * N]; 
vector<int> s[C], v;
bool a1, a2;
int lowbit(int x){return x & -x;}
void input(){
	cin>> n;
	c = n / W + 1; 
	for(int i = 1; i <= n; ++i) cin>> a[i], v.push_back(a[i]);
	sort(v.begin(), v.end());
	v.erase(unique(v.begin(), v.end()), v.end());
	for(int i = 1; i <= n; ++i) a[i] = lower_bound(v.begin(), v.end(), a[i]) - v.begin() + 1; 
	for(int i = 1; i <= n; ++i) s[(i - 1) / W + 1].push_back(a[i]);
	for(int i = 1; i <= c; ++i) sort(s[i].begin(), s[i].end());
	cin>>Q;
}
int count(int v, int nc){
	int ans = 0;
	for(int i = 1; i < nc; ++i){
		auto w = upper_bound(s[i].begin(), s[i].end(), v);
		ans += s[i].end() - w;
	}
	for(int i = nc + 1; i <= c; ++i){
		auto w = lower_bound(s[i].begin(), s[i].end(), v);
		ans += w - s[i].begin();
	}
	int flag = 0;
	
	for(int i = (nc - 1) * W + 1; i <= min(nc * W, n); ++i){
		if(a[i] == v) flag = 1;
		if(flag == 0){
			ans += a[i] > v; 
		}else if(flag == 1){
			ans += a[i] < v;
		}
	} 
	return ans;
}
void del(int v, int nc){
	auto w = lower_bound(s[nc].begin(), s[nc].end(), v);
	s[nc].erase(w);
}
void ins(int v, int nc){
	auto w = upper_bound(s[nc].begin(), s[nc].end(), v);
	s[nc].insert(w, v);
}
void add(int v){
	while(v <= n){
		++tr[v];
		v += lowbit(v);
	}
}
int query(int v){
	long long ans = 0;
	while(v > 0){
		ans += tr[v];
		v -= lowbit(v);
	}
	return ans;
}
void pre(){
	for(int i = 1; i <= n; ++i){
		cnt += query(n) - query(a[i]);
		add(a[i]);
	}
	for(int i = 1; i <= n; ++i){
		cnt2 += abs(a[i] - i);
	}
}
void op(){
	cout<<cnt<<'\n';
	for(int i = 1; i <= Q; ++i){
		cin >> l >> r;
		if(l > r) swap(l, r);
		lc = (l - 1) / W + 1, rc = (r - 1) / W + 1;
		cnt -= count(a[l], lc);
		cnt -= count(a[r], rc);
		if(a[l] > a[r]) cnt++; 
		del(a[l], lc);del(a[r], rc);
		ins(a[l], rc);ins(a[r], lc);
		swap(a[l], a[r]);
		cnt += count(a[l], lc);
		cnt += count(a[r], rc);
		if(a[l] > a[r]) cnt--; 
		cout<<cnt <<'\n';
	} 
}
int main(){
	cin.tie(0)->sync_with_stdio(false);
	input();
	pre();
	op();
}


回复

2 条回复,欢迎继续交流。

正在加载回复...