P6412 [COCI2008-2009#3] BST题解
Naro_Ahgnay · · 题解
严格 \Theta(n) 算法
题目描述
现在有一个序列
注意:第一个数已经作为 BST 的根。
思路
对于每一个答案,分析后可以发现,每个数一定是在已经加入进去的数中小于它的最大值和大于它的最小值的两个数之间。举个例子:
对于数
步骤
step1
首先创造一个链表,链表有两个值,一个是
step2
对于输入的
step3
从1到n正序遍历,对于每一个遍历到的数
code
#include<bits/stdc++.h>
using namespace std;
struct List{
int las,nxt;
}li[300011];
int n;
long long sum;
pair<int,int> b[300001];
int a[300001],dep[300001];
int main()
{
// freopen("P6412.in","r",stdin);
// freopen("P6412.out","w",stdout);
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%d",&a[i]);
li[i].nxt=i+1,li[i].las=i-1;
}
li[0].nxt=1,li[n+1].las=n;
for(int i=n;i;i--)
{
b[a[i]].first=li[a[i]].las,b[a[i]].second=li[a[i]].nxt;
li[li[a[i]].las].nxt=li[a[i]].nxt,li[li[a[i]].nxt].las=li[a[i]].las;
}
dep[a[1]]=0;puts("0");
for(int i=2;i<=n;i++)
{
dep[a[i]]=max(dep[b[a[i]].first],dep[b[a[i]].second])+1;
sum+=dep[a[i]];
printf("%lld\n",sum);
}
return 0;
}