gpt4 book ai didi

haskell - 用 foldr 构建平衡二叉树

转载 作者:行者123 更新时间:2023-12-04 11:54:30 31 4
gpt4 key购买 nike

我写函数foldTree从列表中构建平衡二叉树。
我必须使用 foldr没关系,我用过,但我做了insertInTree函数递归=(现在我只知道这种方式可以穿过树木=))。

更新 : 我不确定功能 insertTree : 递归计算高度是否正确? =((这里需要一些帮助。

可以写insertInTree没有递归(带有 until/iterate/unfoldr 的东西)或制作 foldTree没有辅助函数的函数 => 以某种方式更短?

这是我在下面的尝试:

data Tree a = Leaf
| Node Integer (Tree a) a (Tree a)
deriving (Show, Eq)

foldTree :: [a] -> Tree a
foldTree = foldr (\x tree -> insertInTree x tree) Leaf

insertInTree :: a -> Tree a -> Tree a
insertInTree x Leaf = Node 0 (Leaf) x (Leaf)
insertInTree x (Node n t1 val t2) = if h1 < h2
then Node (h2+1) (insertInTree x t1) val t2
else Node (h1+1) t1 val (insertInTree x t2)
where h1 = heightTree t1
h2 = heightTree t2

heightTree :: Tree a -> Integer
heightTree Leaf = 0
heightTree (Node n t1 val t2) = n

输出:
*Main> foldTree "ABCDEFGHIJ"
Node 3 (Node 2 (Node 0 Leaf 'B' Leaf) 'G' (Node 1 Leaf 'F' (Node 0 Leaf 'C' Leaf))) 'J' (Node 2 (Node 1 Leaf 'D' (Node 0 Leaf 'A' Leaf)) 'I' (Node 1 Leaf 'H' (Node 0 Leaf 'E' Leaf)))
*Main>

最佳答案

当两个子树的高度相等时,您的插入函数是错误的,因为如果它已经满了,插入到正确的子树会增加它的高度。我不清楚您的代码中是否会出现这种情况。

将新元素插入树的明显正确方法似乎是

insertInTree x (Node n t1 val t2) 
| h1 < h2 = Node n (insertInTree x t1) val t2
| h1 > h2 = Node n t1 val t2n
| otherwise = Node (h+1) t1 val t2n
where h1 = heightTree t1
h2 = heightTree t2
t2n = insertInTree x t2
h = heightTree t2n -- might stay the same

这会创建几乎平衡的树(又名 AVL 树)。但是它将每个新元素推到树的最底部。

编辑:可以很好地看到这些树
showTree Leaf = ""  
showTree n@(Node i _ _ _) = go i n
where
go _ (Leaf) = ""
go i (Node _ l c r) = go (i-1) l ++
replicate (4*fromIntegral i) ' ' ++ show c ++ "\n" ++ go (i-1) r

尝试

putStr . showTree $ foldTree "ABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890"



是的,您可以将 foldTree 写得更短,如
foldTree = foldr insertInTree Leaf

关于haskell - 用 foldr 构建平衡二叉树,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16157203/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com