应该可以将 id 转换为树并返回。
id 和位串是:
0 -> 0
1 -> 100
2 -> 11000
3 -> 10100
4 -> 1110000
5 -> 1101000
6 -> 1100100
7 -> 1011000
8 -> 1010100
首先考虑一个事实,给定一个位串,我们可以很容易地移动到树(一种递归方法),反之亦然(预排序,输出 1 表示父节点,0 表示叶节点)。
主要挑战来自尝试将 id 映射到位串,反之亦然。
假设我们列出了 n 个节点的树如下:
Left sub-tree n-1 nodes, Right sub-tree 0 nodes. (Cn-1*C0 of them)
Left sub-tree n-2 nodes, Right sub-tree 1 node. (Cn-2*C1 of them)
Left sub-tree n-3 nodes, right sub-tree 2 nodes. (Cn-3*C2 of them)
...
...
Left sub-tree 0 nodes, Right sub-tree n-1 nodes. (C0*Cn-1 of them)
Cr = rth catalan number.
您给出的枚举似乎来自以下过程:我们保持左子树固定,枚举右子树。然后移动到下一个左子树,枚举右子树,依此类推。我们从最大大小的左子树开始,然后下一个是最大大小-1,依此类推。
所以说我们有一个 id = S 说。我们首先找到一个 n 使得
C0 + C1 + C2 + ... + Cn < S <= C0+C1+ C2 + ... +Cn+1
那么 S 将对应于具有 n+1 个节点的树。
所以你现在考虑 P = S - (C0+C1+C2+ ...+Cn),它是在 n+1 个节点的树的枚举中的位置。
现在我们计算出一个 r 使得 Cn*C0 + Cn-1*C1 + .. + Cn-r Cr < P <= Cn C0 + Cn-1*C1 + .. + Cn-r+1*Cr-1
这告诉我们左子树和右子树有多少个节点。
考虑到 P - Cn*C0 + Cn-1*C1 + .. + Cn-r*Cr ,我们现在可以计算出精确的左子树枚举位置(仅考虑该大小的树)和精确的右子树枚举位置并递归形成位串。
将位串映射到 id 应该是类似的,因为我们知道左子树和右子树是什么样的,我们需要做的就是找到相应的位置并做一些算术来获得 ID。
不确定它有多大帮助。您将一直在处理一些非常庞大的数字。