This question uses the combination of weighted line tree.
First, let's talk about two concepts in the solution: Combination of weighted line tree and line tree.
The so-called weighted line segment tree can be understood as a normal line segment tree with maintenance information in turn. I personally think that the name of the Value Line Segment tree must be accurate.
For example, we insert the numbers in the sequence $, 4, $ in sequence. After the insertion is complete, the following is probably the result:
(Red indicates the value of the node)
That is to say, the value maintained by each node is the number of occurrences of the number in this interval.
When implementing a weight line segment tree, we usually adopt a dynamic open-point approach, that is, we do not create irrelevant nodes. Of course, we can also discretization data. Otherwise, the space will inevitably exceed the limit.
The principle of line Tree merging is based on the stable structure of the line tree.
In the process of merging, we combine the values of the nodes at the corresponding positions of the two line segment trees to create a new line segment tree.
The process is roughly as follows:
This question allows us to find the minimum number of pairs in reverse order, and allows us to freely swap two Subtrees of one node.
Considering an arbitrary node, its subtree has only three reverse order pairs after first traversal:
1. Left subtree
2. right subtree
3. span left and right subtree
The switch between Subtrees obviously does not affect the first and second classes. Therefore, we only need to calculate the minimum values of the third class.
As for computing, there is no difficulty. Because we maintain a value range, the left son must be bigger than the right son, so we can use the left son size multiplied by the right son size to obtain the number of reverse pairs before the exchange. The same is true after the exchange.
Note that we can calculate this because, no matter how the right and right sons exchange, only the number of Reverse Order pairs in the current part will be affected, without affecting the values of nodes with a lighter depth.
In addition, the input for processing this question is very suffocated. You can refer to the instructions below.
The AC code is as follows:
509 Ms 57236kb
1 #include<bits/stdc++.h> 2 3 using namespace std; 4 5 namespace StandardIO { 6 7 template<typename T>inline void read (T &x) { 8 x=0;T f=1;char c=getchar(); 9 for (; c<‘0‘||c>‘9‘; c=getchar()) if (c==‘-‘) f=-1;10 for (; c>=‘0‘&&c<=‘9‘; c=getchar()) x=x*10+c-‘0‘;11 x*=f;12 }13 14 template<typename T>inline void write (T x) {15 if (x<0) putchar(‘-‘),x*=-1;16 if (x>=10) write(x/10);17 putchar(x%10+‘0‘);18 }19 20 }21 22 using namespace StandardIO;23 24 namespace Solve {25 26 const int N=200200;27 28 int n;29 long long ans,ans1,ans2;30 int tot_node;31 struct node {32 int ls,rs;33 long long val;34 } tree[N*20];35 36 void update (int l,int r,int v,int &pos) {37 if (!pos) pos=++tot_node;38 tree[pos].val++;39 if (l==r) return;40 int mid=(l+r)>>1;41 if (v<=mid) update(l,mid,v,tree[pos].ls);42 else update(mid+1,r,v,tree[pos].rs);43 }44 void merge (int &x,int y) {45 if (!x||!y) {46 x=x+y;return;47 }48 tree[x].val+=tree[y].val;49 ans1+=(long long)tree[tree[x].rs].val*tree[tree[y].ls].val;50 ans2+=(long long)tree[tree[x].ls].val*tree[tree[y].rs].val;51 merge(tree[x].ls,tree[y].ls);52 merge(tree[x].rs,tree[y].rs);53 }54 void dfs (int &x) {55 int tmp,ls,rs;x=0;56 read(tmp);57 if (!tmp) {58 dfs(ls),dfs(rs);59 ans1=ans2=0;60 x=ls,merge(x,rs);61 ans+=min(ans1,ans2);62 } else update(1,n,tmp,x);63 }64 65 inline void solve () {66 read(n);67 int tmp=0;68 dfs(tmp);69 write(ans);70 }71 }72 73 using namespace Solve;74 75 int main () {76 // freopen(".in","r",stdin);77 // freopen(".out","w",stdout);78 solve();79 }
Solution p3521 [[poi2011] rot-tree rotations]