Loading docs/ds/cartesian-tree.md +10 −11 Original line number Diff line number Diff line Loading @@ -25,18 +25,17 @@ author: sshwy, zhouyuyang2002, StudyingFather, Ir1d, ouuan, Enter-tainer 显然每个数最多进出右链一次(或者说每个点在右链中存在的是一段连续的时间)。这个过程我们可以用栈维护,栈中维护当前笛卡尔树的右链上的结点。一个点不在右链上了就把它弹掉。这样每个点最多进出一次,复杂度 $O(n)$ 。伪代码如下: ```text 新建一个大小为n的空栈。 新建一个大小为n的空栈。用top来标操作前的栈顶,k来标记当前栈顶。 For i:=1 to n flag = 0 While 栈不为空 if 栈顶元素<当前元素 int k=top While 栈非空且栈顶元素>当前元素 k-- if 栈非空 栈顶元素.右儿子=当前元素 break else 栈顶元素.右儿子=当前元素.左儿子。 if k<top 当前元素.左儿子=栈顶元素 栈顶元素出栈 当前元素入栈。 当前元素入栈 top=k ``` ## 笛卡尔树与 Treap Loading Loading
docs/ds/cartesian-tree.md +10 −11 Original line number Diff line number Diff line Loading @@ -25,18 +25,17 @@ author: sshwy, zhouyuyang2002, StudyingFather, Ir1d, ouuan, Enter-tainer 显然每个数最多进出右链一次(或者说每个点在右链中存在的是一段连续的时间)。这个过程我们可以用栈维护,栈中维护当前笛卡尔树的右链上的结点。一个点不在右链上了就把它弹掉。这样每个点最多进出一次,复杂度 $O(n)$ 。伪代码如下: ```text 新建一个大小为n的空栈。 新建一个大小为n的空栈。用top来标操作前的栈顶,k来标记当前栈顶。 For i:=1 to n flag = 0 While 栈不为空 if 栈顶元素<当前元素 int k=top While 栈非空且栈顶元素>当前元素 k-- if 栈非空 栈顶元素.右儿子=当前元素 break else 栈顶元素.右儿子=当前元素.左儿子。 if k<top 当前元素.左儿子=栈顶元素 栈顶元素出栈 当前元素入栈。 当前元素入栈 top=k ``` ## 笛卡尔树与 Treap Loading