Cartesian Tree
Introduction
A Cartesian tree is a binary tree where each node consists of a key-value pair \((k,w)\). It requires that \(k\) satisfies the properties of a Binary Search Tree (BST), while \(w\) satisfies the properties of a heap. If the key-values \((k,w)\) of the Cartesian tree are determined, and all \(k\) are distinct and all \(w\) are distinct, then the structure of this Cartesian tree is unique. As shown in the figure below:

(Image source: Wikipedia)
The Cartesian tree above treats the array element values as the key \(w\), and the array indices as the key \(k\). It can be observed that the key \(k\) of this tree satisfies BST properties, while the key \(w\) satisfies the properties of a min-heap. Moreover, due to the properties of a binary search tree, it can be seen that for this special Cartesian tree, the indices within a subtree form a contiguous interval.
In competitive programming, when using Cartesian trees, array indices are often used as the key \(k\) of the pair, and the array index \(k\) satisfies BST properties.
In the following, when using \(k,w\), it is assumed by default that \(k\) satisfies BST properties and \(w\) satisfies heap properties.
Building a Cartesian Tree with a Monotonic Stack
Process
We consider inserting elements into the current Cartesian tree in ascending order of \(k\).
For a Cartesian tree, define the "right chain" as the chain formed by starting from the root node and continuously moving to the right child until reaching a leaf node. Then, after inserting a node, this node must be on the right chain. Because we are inserting in ascending order of \(k\) which satisfies BST properties, this newly inserted node must be at the rightmost end of the tree. This node cannot be a left child and has no right child.
Thus, we perform the following process: compare the \(w\) values of nodes on the right chain with the current node \(u\) from bottom to top. If we find a node \(x\) on the right chain satisfying \(w_x<w_u\), we attach \(u\) as the right child of \(x\), and the original right subtree of \(x\) becomes the left subtree of \(u\).
The red box in the figure shows the right chain we maintain:

Clearly, each number enters and exits the right chain at most once (or each point exists on the right chain for a contiguous period of time). This process can be maintained using a monotonic stack, where the stack stores the nodes currently on the right chain of the Cartesian tree. A point is popped from the stack when it is no longer on the right chain. Thus, each point enters and exits at most once, resulting in a complexity of \(O(n)\).
Cartesian Tree and Treap
In fact, a Treap is a type of Cartesian tree, except that in a Treap, the value \(w\) is completely random. Treaps have a linear construction algorithm. If the keys \(k\) are sorted in advance, the above monotonic stack algorithm can be used for construction, though it is rarely used this way.
C++ Implementation
1 2 3 4 5 6 7 8 9 | |
Example Problems
HDU 1506. Largest Rectangle in a Histogram
There are \(n\) positions, each with a height \(h_i\). Find the largest sub-rectangle. As shown in the figure:

The shaded part is the largest sub-rectangle in the figure.
Solution Idea
Specifically, we treat the index as the key \(k\), and \(h_i\) as the key \(w\) satisfying min-heap properties, constructing a Cartesian tree of \((i,h_i)\).
Then we enumerate each node \(u\), taking \(w_u\) (i.e., the height \(h\) of node \(u\)) as the height of the largest sub-rectangle. Since the Cartesian tree we built satisfies min-heap properties, the heights of nodes in the subtree of \(u\) are all greater than or equal to \(u\). Moreover, we know that the indices within the subtree of \(u\) form a contiguous interval. Thus, we only need to know the size of the subtree to calculate the area of the largest sub-rectangle for this interval. Update the answer with the value computed for each point. Clearly, this can be done with a single DFS, so the complexity is \(O(n)\).
Reference Implementation
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 | |
References
本页面最近更新:,更新历史
发现错误?想一起完善? 在 GitHub 上编辑此页!
本页面贡献者:OI-wiki
本页面的全部内容在 CC BY-SA 4.0 和 SATA 协议之条款下提供,附加条款亦可能应用