Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/haskell/8.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Function 如何在Haskell中的树之间移动子树?_Function_Haskell_Recursion_Types_Functional Programming - Fatal编程技术网

Function 如何在Haskell中的树之间移动子树?

Function 如何在Haskell中的树之间移动子树?,function,haskell,recursion,types,functional-programming,Function,Haskell,Recursion,Types,Functional Programming,对于两个多路树t1和t2,使用 type Forest a = [Tree a] data Tree a = Node { rootLabel :: a, subForest :: Forest a } 如何编写一个函数,从t1中删除子树并将其插入t2中的给定节点 我想签名应该是这样的 moveSubTree :: ((Tree x a) x (Tree x a)) -> (Tree x Tree) i、 它需要一个树和父节点来定义

对于两个多路树t1和t2,使用

type Forest a = [Tree a]
data Tree a   = Node {
        rootLabel :: a,     
        subForest :: Forest a
    }
如何编写一个函数,从t1中删除子树并将其插入t2中的给定节点

我想签名应该是这样的

moveSubTree :: ((Tree x a) x (Tree x a)) -> (Tree x Tree)
i、 它需要一个树和父节点来定义要删除的子树,以及第二个树和节点来定义插入原始子树的点


如果需要,可以组合用于删除和添加子树的单独函数。

您可以在树中进行编辑和读取“在路径上”

data Dir    = L | R
type Path   = [Dir]
data Tree a = Leaf | Node a (Tree a) (Tree a)

read :: Path -> Tree a -> Maybe (Tree a)
read []     t = t
read (s:ss) t = case t of
  Leaf       -> Nothing
  Node a l r -> case s of
    L -> read ss l
    R -> read ss r

edit :: Path -> (Tree a -> Tree a) -> Tree a -> Maybe (Tree a)
edit []     f t = Just (f t)
edit (s:ss) f t = case t of
  Leaf       -> Nothing
  Node a l r -> case s of
    L -> do
      l' <- edit ss f l
      return (Node a l' r)
    R -> do
      r' <- edit ss f r
      return (Node a l r')
data Dir=L | R
类型路径=[Dir]
数据树a=叶|节点a(树a)(树a)
阅读::路径->树a->可能(树a)
读取[]t=t
read(s:ss)t=的情况t
叶->无
节点a l r->案例s
读短文
R->读取ss R
编辑::路径->(树a->树a)->树a->可能(树a)
编辑[]f t=刚刚(f t)
编辑(s:ss)f t=案例t
叶->无
节点a l r->案例s
L->do

什么是
x
?此外,Haskell没有指针。树值只是一棵树,而不是任何事物的子树。你需要提供一些从树中获取子树的方法,比如路径(一个索引列表)。你必须比“…在t2中的给定深度插入它”更具体——在任何给定深度的树中可能有几个点,你想将它移动到哪个点?这是有意义的——我应该把“在t2中的给定节点插入它”。我将更新这个问题以反映这一点。一个小的挑剔,TS想要一个多路树,而不是二进制。真的。这个想法通过使用
type Path=[Int]
并注意到路径太长和引用不存在的子树都可能“丢失”,从而推广到多路树。
cnp :: Path -> Path -> Tree a -> Maybe (Tree a)
cnp readPath writePath t = do
  subtree <- read readPath t
  edit writePath (const subtree) t