Dictionary Haskell:更新二叉树

Dictionary Haskell:更新二叉树,dictionary,haskell,binary-tree,Dictionary,Haskell,Binary Tree,我想实现一个映射函数mapLeaves,该函数只映射到二叉树中的叶子,并返回一个更新后的树 data Tree = TNode Int [Tree] | Tleaf Int -1 / \ -5 10 / \ -4 30 / \ 13 17 t = TNode (-1) [TNode (-5) [ TNode (-4) [ Tleaf 13, Tleaf 17] , Tle

我想实现一个映射函数mapLeaves,该函数只映射到二叉树中的叶子,并返回一个更新后的树

data Tree = TNode Int [Tree] | Tleaf Int

    
         -1
        /   \
      -5     10
      / \   
    -4  30  
    / \
   13  17

t = TNode (-1) [TNode (-5)  [  TNode (-4) [ Tleaf 13, Tleaf 17] ,  Tleaf 30 ] ,Tleaf 10 ]

getListLeaves (Tleaf x)= [x]
getListLeaves (TNode x [Tleaf y])=[y]
getListLeaves (TNode x (y:ys))=  (getListLeaves y) ++ (getListLeaves (TNode x ys)) 

mapLeaves f tree = map (f) (getListLeaves tree)
枫叶(+3)t 然后得到答案 [16,20,33,13]

这就是我停下来的地方,我如何把这个列表变成一个二叉树,就像上面显示的t一样,它的叶子被更新了,但节点仍然存在。 提前谢谢

编辑: 为什么会这样

sumLeaves :: Tree -> Int
sumLeaves (Tleaf x)=x
sumLeaves (TNode n xs)=sum (map sumLeaves xs)
但当我把sum改为TNode n时,它就不起作用了

sumLeaves :: Tree -> Int
sumLeaves (Tleaf x)=x
sumLeaves (TNode n xs)=TNode n (map sumLeaves xs)
这也是我坚持的地方

mapLeaves :: (Int -> Int) -> Tree -> Tree
mapLeaves f (Tleaf x) = Tleaf (f x)
mapLeaves f (TNode x cs)=TNode x  (map mapLeaves f cs)

首先不要使用列表。现在“关于结构的信息”丢失了。使用递归映射树中的元素

因此,您可以将其实现为:

mapLeaves :: (Int -> Int) -> Tree -> Tree
mapLeaves f (Tleaf x) = …
mapLeaves f (TNode x cs) = TNode x (…)
mapLeaves::(Int->Int)->Tree->Tree
枫叶f(Tleaf x)=…
mapLeaves f(TNode x cs)=TNode x(…)
您需要在此处填写
部分。因此,对于
TNode
部分,您将创建一个新的
TNode
,并将
x
作为值,然后在树的子级
cs
上递归


然而,建模有点奇怪。虽然可以表示二叉树,但数据类型不强制二叉树:因为
TNode
可以有零个、一个或多个子节点。此外,一个没有子节点的
TNode
可能是一个叶子,但是你有一个额外的数据构造函数,这意味着同一棵(二叉)树可以用多种方式表示,这通常不是一个好主意。

首先不要使用列表。现在“关于结构的信息”丢失了。使用递归映射树中的元素。好的,我解决了它,谢谢,我真的很笨。。