1099: [POI2007] Tree drz time limit: $ Sec Memory Limit: 162 MB
Submit: 142 Solved: 55
[Submit] [Status] Description
CDQZ is a remote elementary school, and FGD has a row of trees in its schools. He did not like the order of the trees, for they were so uneven in height and height. FGD defines the degree of ataxia of these trees as well as the height difference of the two adjacent trees. The height of the tree was H1,h2,h3,..., HN respectively. Then the degree of ataxia is defined as: |h1-h2|+|h2-h3|+......+|hn-1-hn|. However, re-planting these trees is a hassle, so FGD only wants to swap the locations of the two trees. Now ask you to help him, how he should exchange the smallest degree of ataxia in the whole row of trees.
Input
The first line contains an integer n (2<=n<= 50000), and the second row contains n positive integers h1,h2,h3,..., hn, representing the height of the tree, respectively. (1<=hi<=100000000)
Output
Should contain n rows, an integer per line, and line I indicates the minimum amount of ataxia that can be obtained if one of the trees in the interchange is numbered I.
Sample InputSample Input 1
5
7 4 5) 2 5
Sample Input 2
5
1 2 3) 4 5
Sample OutputSample Output 1
7
7
8
7
7
Sample Output 2
4
4
4
4
4HINT
Source
[Submit] [Status]
The subject is a sort of lunatic discussion
Obviously, if you consider changing hi, the optimal solution is to change with the HJ
so hi has the smallest, the second small, the largest (relative to I on both sides of the tree) 3 kinds of situations, HJ also has (relative J on both sides)
So it can be divided into 3*3 kinds of situation
The insertion order of the segment tree maintains the HJ condition and fits the conditions into the segment tree.
As for Hi, of course, directly on the line tree.
The cost difference formula of the column Exchange is analyzed in 9 cases respectively.
Special:
Note that the Hi,hi left and right 2 sides maximum, left and right 2-side min. sort discretization into the tree, because the value of hi is pressed when inserting the tree
#include <cstdio> #include <cstring> #include <cstdlib> #include <algorithm> #include < functional> #include <iostream> #include <cmath> #include <cctype> #include <ctime> #include <vector>using namespace std; #define for (I,n) for (int. i=1;i<=n;i++) #define FORK (i,k,n) for (int i=k;i<=n;i++ ) #define REP (I,n) for (int. i=0;i<n;i++) #define ForD (I,n) for (int. i=n;i;i--) #define FORKD (i,k,n) for (int i=n;i>=k; i--) #define REPD (I,n) for (int. i=n;i>=0;i--) #define FORP (x) for (int p=pre[x];p, p=next[p]) #define FORPITER (x) for (int &p=iter[x];p; p=next[p]) #define LSON (x<<1) #define Rson ((x<<1) +1) #define MEM (a) memset (A,0,sizeof (a) ), #define MEMI (a) memset (A,127,sizeof (a)), #define MEMI (a) memset (A,128,sizeof (a)), #define INF (2139062143) #define F ( 100000007) #define MAXN (50000+10) #define MAXH (100000000+10) long long mul (long long A,long long B) {return (a*b)%F;} Long Long (long A,long long B) {return (a+b)%F;} A long long sub (long longA,long long B) {return (a-b+ (a)/f*f+f)%F;} typedef long Long Ll;int n,pos[maxn],lpos[maxn],rpos[maxn],himinpos[maxn],himaxpos[maxn];ll H[MAXN],HIMAX[MAXN], HIMIN[MAXN],ANS[MAXN],V[MAXN];p air<ll,int> h2[maxn];class segmenttree{ll a[maxn*4],minv[maxn*4];int n;public : Segmenttree () {mem (a) mem (MINV)}segmenttree (int _n): N (_n) {mem (a) mem (MINV)}void mem (int _n) {n=_n; Memi (a) Memi (MINV)}int p,v; Set a[p]=vvoid set (int p,int v) {this->p=p,this->v=v;_set (1,1,n);} void _set (int x,int l,int R) {int m= (l+r) >>1;if (l==r) {A[x]=minv[x]=v;return;} Else{if (p<=m) _set (lson,l,m); else _set (rson,m+1,r);} minv[x]=min (Minv[lson],minv[rson]);} int ql,qr;ll query_min (int ql,int qr) {this->ql=ql,this->qr=qr;if (QL>QR) return Inf;return _query_min (1,1,n);} ll _query_min (int x,int l,int R) {if (QL<=L&&R<=QR) return minv[x];ll ans=inf,m= (l+r) >>1;if (ql<= M) Ans=min (Ans,_query_min (lson,l,m)), if (m< qr) ans=min (Ans,_query_min (rson,m+1,r)); return ans;}} S;int t_n;ll dis (int I,int j) {return abs (H[i]-h[j]);} void Pre_work () {MEM (ANS)//One at the end, the other in non-end, not adjacent Fork (i,3,n-1) {ll Tmp=-dis (+dis (i,2)-v[i]+dis (1,i-1) +dis (1,i+1); Ans[1]=min (ans[1],tmp); Ans[i]=min (ans[i],tmp);} Fork (i,2,n-2) {ll tmp=-dis (n,n-1) +dis (i,n-1)-v[i]+dis (n,i-1) +dis (n,i+1); Ans[n]=min (ans[n],tmp); Ans[i]=min (ans[i) , TMP);} No end-to-end, adjacent Fork (i,2,n-2) {ll tmp=-dis (i,i-1)-dis (i+1,i+2) +dis (i+1,i-1) +dis (i,i+2); Ans[i]=min (ans[i],tmp); ans[i+1]= Min (ans[i+1],tmp);} One at the end, the other in the non-end, adjacent 1и2 or (n-1) иn ll Tmp=-dis (2,3) +dis (1,3); Ans[1]=min (ans[1],tmp); Ans[2]=min (ans[2],tmp); Tmp=-dis ( n-2,n-1) +dis (n-2,n) ans[n]=min (ans[n],tmp) ans[n-1]=min (ans[n-1],tmp);//end-to-end, non-adjacent Tmp=-dis (-dis) n-1,n (+dis ) +dis (1,n-1); Ans[1]=min (ans[1],tmp); Ans[n]=min (ans[n],tmp);} struct Node{int i,flag;ll A;node () {}node (int _i,int _flag,ll _a): I (_i), Flag (_flag), a (_a) {}void print () {Cout<<i << ': ' <<flag<< ' <<a<<endl; }}a[3*maxn];int m;int cmp1 (const void* a,const void *b)// -1,0,1{node _a=* (node*) a,_b=* (node*) b;if (_A.A^_B.A) return _a.a-_b.a;else return _a.flag-_b.flag;} int CMP2 (const void* a,const void *b)//case#1:0,-1 case#3:1,0 {node _a=* (node*) a,_b=* (node*) b;if (_A.A^_B.A) return _a. A-_b.a;else return _b.flag-_a.flag;} int fee_u[4][4]={{},{0,1,1,-2},{0,-1,1,0},{0,-1,-1,2}};void fee (int i,int j,int flagj,int flagi,ll &tmp,ll & Add) {tmp=-v[i]+fee_u[flagj+2][1]*himin[i]+fee_u[flagj+2][2]*himax[i]+fee_u[flagi+2][3]*h[i];add=-v[j]+fee_u[ FLAGJ+2][3]*H[J]+FEE_U[FLAGI+2][1]*HIMIN[J]+FEE_U[FLAGI+2][2]*HIMAX[J];} ll fee_tmp (int i,int flagj,int Flagi) {return-v[i]+fee_u[flagj+2][1]*himin[i]+fee_u[flagj+2][2]*himax[i]+fee_u[ Flagi+2][3]*h[i];} ll fee_add (int j,int flagj,int Flagi) {return-v[j]+fee_u[flagj+2][3]*h[j]+fee_u[flagi+2][1]*himin[j]+fee_u[flagi+2] [2]*himax[j];} BOOL B[maxn];void WORK1 (const int FLAGJ)//( -1,FLAGJ) {//cout<< "--------------------------\ n"; MEM (b) const int flagi=-1; Qsort (a+1,m,sizeof (node), CMP2); S.mem (T_n); ForD (i,m) {node now=a[i];if (now.flag==-1) {S.set (pos[Now.i],fee_add (Now.i,flagj,flagi)],b[pos[now.i]]=1;//cout<< "add:" <<pos[now.i]<< "<< Fee_add (Now.i,flagj,flagi) <<endl; }else if (now.flag==0) {ll tmp=fee_tmp (Now.i,flagj,flagi), Add;bool b1=0,b2=0;ll t1=0,t2=0;if (B[pos[now.i-1]]) {b1=1; S.set (Pos[now.i-1],inf);//cout<< "1del:" <<pos[now.i-1]<<endl; }if (B[pos[now.i+1]]) {b2=1; S.set (Pos[now.i+1],inf);//cout<< "1del:" <<pos[now.i+1]<<endl; }if (flagj==-1) add=s.query_min (1,rpos[himinpos[now.i]); else if (flagj==0) add=s.query_min (LPOS[HIMINPOS[NOW.I]], RPOS[HIMAXPOS[NOW.I]); else Add=s.query_min (lpos[himaxpos[now.i]],t_n);//cout<<now.i<< ' << flagj<< ' <<lpos[himaxpos[now.i]]<< ' <<tmp<< ' <<add<<endl; Ans[now.i]=min (Ans[now.i],tmp+add); if (B1) {S.set (Pos[now.i-1],fee_add (Now.i-1,flagj,flagi));//cout<< "1add:" <<pos[now.i-1]<<endl;} if (B2) {S.set (Pos[now.i+1],fee_add (Now.i+1,flagj,flagi));//cout<< "1add: "<<pos[now.i+1]<<endl;}}} void Work2 (const int FLAGJ)//(0,FLAGJ) {//cout<< "--------------------------\ n"; MEM (b) const int flagi=0; Qsort (a+1,m,sizeof (node), CMP1); S.mem (T_n); ForD (i,m) {node now=a[i];if (now.flag==1) {S.set (Pos[now.i],fee_add (Now.i,flagj,flagi)),b[pos[now.i]]=1;//cout< < "add:" <<pos[now.i]<< "<<fee_add (Now.i,flagj,flagi) <<endl;} else if (now.flag==-1) {s.set (Pos[now.i],inf),b[pos[now.i]]=0;//cout<< "del:" <<pos[now.i]<<endl;} else if (now.flag==0) {ll tmp=fee_tmp (Now.i,flagj,flagi), Add;bool b1=0,b2=0;ll t1=0,t2=0;if (B[pos[now.i-1]]) {b1=1; S.set (Pos[now.i-1],inf);//cout<< "1del:" <<pos[now.i-1]<<endl; }if (B[pos[now.i+1]]) {b2=1; S.set (Pos[now.i+1],inf);//cout<< "1del:" <<pos[now.i+1]<<endl; }if (flagj==-1) add=s.query_min (1,rpos[himinpos[now.i]); else if (flagj==0) add=s.query_min (LPOS[HIMINPOS[NOW.I]], RPOS[HIMAXPOS[NOW.I]]); else add=s.query_min (lpos[himaxpos[now.i]],t_n);//for (Pi,n) cout<<s.query_min (PI,PI) << ";cout<<" Test "<<endl;ans[now.i]=min (ans[now.i],tmp+add ); if (B1) {S.set (Pos[now.i-1],fee_add (Now.i-1,flagj,flagi));//cout<< "1add:" <<pos[now.i-1]<<endl;} if (B2) {S.set (Pos[now.i+1],fee_add (Now.i+1,flagj,flagi));//cout<< "1add:" <<pos[now.i+1]<<endl;}} }void WORK3 (const int FLAGJ)//(1,FLAGJ) {//cout<< "--------------------------\ n"; MEM (b) const int flagi=1; Qsort (a+1,m,sizeof (node), CMP2); S.mem (T_n); Fork (i,2,t_n-1) S.set (Pos[i],fee_add (I,flagj,flagi)), b[pos[i]]=1; ForD (i,m) {node now=a[i];//now.print (); if (now.flag==1) {s.set (Pos[now.i],inf),b[pos[now.i]]=0;//cout<< "del: "<<pos[now.i]<<endl;} else if (now.flag==0) {ll tmp=fee_tmp (Now.i,flagj,flagi), Add;bool b1=0,b2=0;ll t1=0,t2=0;if (B[pos[now.i-1]]) {b1=1; S.set (Pos[now.i-1],inf);//cout<< "1del:" <<pos[now.i-1]<<endl; }if (B[pos[now.i+1]]) {b2=1; S.set (Pos[now.i+1],inf); cout<< "1del:" <<pos[now.i+1]<<endl; }if (flagj==-1) add=s.query_min (1,rpos[himinpos[now.i]); else if (flagj==0) add=s.query_min (LPOS[HIMINPOS[NOW.I]], RPOS[HIMAXPOS[NOW.I]]); else add=s.query_min (lpos[himaxpos[now.i]],t_n);//for (pi,n) cout<<s.query_min (pi,pi ) << ';cout<< ' Test ' <<endl;//cout<<now.i<< ' <<flagj<< ' <<lpos[ himinpos[now.i]]<< ' <
Bzoj 1099 ([POI2007] Tree Drz-9 sub-segment Tree & Category discussion + segment tree and Insertion Order Maintenance 2 parameters)