GPLT2020L3-2Splay

Posted goto_1600

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了GPLT2020L3-2Splay相关的知识,希望对你有一定的参考价值。

#include<bits/stdc++.h>
using namespace std;
const int N=600010;
#define int long long
struct Node

	int s[2], p, v;
	int size; // 记录以当前节点为根的子树的节点总数
	void init(int _v, int _p) 
		v = _v, p = _p;
		size = 1;
	
tr[N]; 
void pushup(int u)

	tr[u].size = tr[tr[u].s[0]].size + tr[tr[u].s[1]].size + 1;


void rotate(int x)

	int y = tr[x].p, z = tr[y].p;
	int k = tr[y].s[1] == x;
	tr[z].s[tr[z].s[1] == y] = x, tr[x].p = z;
	tr[y].s[k] = tr[x].s[k ^ 1], tr[tr[x].s[k ^ 1]].p = y;
    tr[x].s[k ^ 1] = y, tr[y].p = x;
    pushup(y), pushup(x);


void splay(int x, int k)

	while (tr[x].p != k) 
		int y = tr[x].p, z = tr[y].p;
		if (z != k) 
			if ((tr[y].s[1] == x) ^ (tr[z].s[1] == y)) rotate(x);
			else rotate(y);
		
		rotate(x);
	


int get_k(int k, int u)

	swap(k,u);
	while (u) 
		if (tr[tr[u].s[0]].size >= k) u = tr[u].s[0];
		else if (tr[tr[u].s[0]].size + 1 == k) return tr[u].v;
		else k -= tr[tr[u].s[0]].size + 1, u = tr[u].s[1];
	
	return -1;

vector<int>v[N];
int n,q;
struct Q
	int x1,x2,y1,y2;
query[N];
int idx=0;
int build(int l, int r, int p, int id)

    int mid = l + r >> 1;
	int u = ++ idx;
    tr[u].init(id, p);
	v[id][mid] = u;
    if (l < mid) tr[u].s[0] = build(l, mid - 1, u, id);
    if (mid < r) tr[u].s[1] = build(mid + 1, r, u, id);
    pushup(u);
    return u;

signed main()

	cin>>n>>q;
	for(int i=1;i<=n;i++)
	
		v[i].push_back(0);
		v[i].push_back(1e9);
	
	for(int i=1;i<=q;i++)
	
		string s;
		cin>>s;
		int x1,x2,y;
		cin>>x1>>x2>>y;
		v[x1].push_back(y);
		v[x2].push_back(y);
		query[i]=x1,x2,y,y;
	
	for(int i=1;i<=n;i++)
	
		// ver[i].resize(v[i].size());
		sort(v[i].begin(),v[i].end());
		v[i].erase(unique(v[i].begin(),v[i].end()),v[i].end());
	
	for(int i=1;i<=q;i++)
	
		query[i].y1=lower_bound(v[query[i].x1].begin(),v[query[i].x1].end(),query[i].y1)-v[query[i].x1].begin();
		query[i].y2=lower_bound(v[query[i].x2].begin(),v[query[i].x2].end(),query[i].y2)-v[query[i].x2].begin();
	
	for(int i=1;i<=n;i++)
	
		build(0,v[i].size()-1,0,i);
	
	long long res=0;
	for(int i=1;i<=n;i++)
		res+=1ll*i*i;
	for(int i=1;i<=q;i++)
	
		int x1=query[i].x1;
		int x2=query[i].x2;
		int y1=query[i].y1;
		int y2=query[i].y2;
		int u1=v[x1][y1];
		int u2=v[x2][y2];
		splay(u1,0);
		splay(u2,0);
		pushup(u1);
		pushup(u2);
		int l1=get_k(u1,1);
		int r1=get_k(u1,tr[u1].size);
		int l2=get_k(u2,1);
		int r2=get_k(u2,tr[u2].size);
		res-=1ll*l1*r1;
		res-=1ll*l2*r2;
		res+=1ll*l1*r2;
		res+=1ll*l2*r1;
		tr[tr[u1].s[1]].p=u2;
		tr[tr[u2].s[1]].p=u1;
		swap(tr[u1].s[1],tr[u2].s[1]);
		pushup(u1),pushup(u2);
		cout<<res<<"\\n";
	
	
	return 0;

以上是关于GPLT2020L3-2Splay的主要内容,如果未能解决你的问题,请参考以下文章

L1-023. 输出GPLT

L1-023. 输出GPLT

L1-023 输出GPLT (20 分)

二叉树

L1-023 输出GPLT

wikioi 1029 中序遍历总数