Haskell HXT 拆分 XML 数据

问题描述 投票:0回答:1

我对箭头还很陌生,所以对我要轻松一些......

我正在尝试计算 XML 文件中特定节点的数量。 XML 文件的布局使得在根下有一个场景列表,在每个场景下有一个图层列表,每个图层都有一个名为“recs”的节点。我想计算每个场景中的矩形数量。我不太明白 HXT 是如何工作的。

我将复制导致问题的代码摘录

process :: IOSArrow XmlTree [XmlTree]
process getScene >>. map func
    where func a = a >>> getLayer >>> getRec

每个 get 函数的类型都是

IOSArrow XmlTree XmlTree

为什么这不起作用?我该如何解决它?

错误信息:

count_dirty.hs:20:16: error:
    • Couldn't match type ‘Data.Tree.NTree.TypeDefs.NTree XNode’
                     with ‘IOSLA (XIOState ()) a0 XmlTree’
      Expected type: [XmlTree] -> [IOSLA (XIOState ()) a0 XmlTree]
        Actual type: [IOSLA (XIOState ()) a0 XmlTree]
                     -> [IOSLA (XIOState ()) a0 XmlTree]
    • In the second argument of ‘(>>.)’, namely ‘map func’
      In the second argument of ‘(>>>)’, namely ‘getScene >>. map func’
      In the expression:
        readDocument [withValidate no] file >>> getScene >>. map func
   |
20 |   getScene >>. map func
   |                ^^^^^^^^

谢谢!

haskell arrow-abstraction hxt
1个回答
1
投票

您在这里声明

func
是一个辅助函数,它需要一些
a
,然后计算
a >>> getLayer >>> getRec

getRec :: IOSArrow XmlTree XmlTree
(>>>)  :: (Category cat) => cat a b -> cat b c -> cat a c

GHC 可以推断出

a >>> getRec
意味着
cat ~ IOSArrow, b ~ XmlTree, c ~ XmlTree
,将变量
a
保留为未确定的类型
IOSArrow a XmlTree
,所以

func :: a -> IOSArrow XmlTree XmlTree

还有

map :: (x -> y) -> [x] -> [y]

map func :: [a] -> [IOSArrow XmlTree XmlTree]

自从

(>>.) :: a b c -> ([c] -> [d]) -> a b d 

getScene >>. :: ([XmlTree] -> [d]) -> IOSArrow XmlTree d

现在 GHC 非常确定

a ~ XmlTree, d ~ IOSArrow XmlTree XmlTree
,给予

getScene >>. map func 
  :: IOSArrow 
       XmlTree 
       (IOSArrow XmlTree XmlTree)

问题来自于你的

map func
-
>>.
期望一个纯函数作为它的第二个参数。
func
,在你的例子中,是一个产生箭头的函数,它不是纯的。

我猜你可能想使用 applyA ,它可以让你从输入生成一个箭头,然后应用该箭头,这正是你在这里所做的。在这种情况下,你会写

process = applyA (getScene >>. map func)
    ...

请注意,您正在使用列表箭头,因此类型签名就是

process :: IOSArrow XmlTree XmlTree
© www.soinside.com 2019 - 2024. All rights reserved.