Я пытаюсь использовать HXT для чтения некоторых больших файлов данных XML (сотни МБ).
Мой код имеет утечку пространства где-то , но я не могукажется, нашел это.Я немного разбираюсь в том, что происходит, благодаря моим очень ограниченным знаниям о цепочке инструментов профилирования ghc.
По сути, документ анализируется, но не оценивается.
Вот некоторый код:
{-# LANGUAGE Arrows, NoMonomorphismRestriction #-}
import Text.XML.HXT.Core
import System.Environment (getArgs)
import Control.Monad (liftM)
main = do file <- (liftM head getArgs) >>= parseTuba
case file of(Left m) -> print "Failed."
(Right _) -> print "Success."
data Sentence t = Sentence [Node t] deriving Show
data Node t = Word { wSurface :: !t } deriving Show
parseTuba :: FilePath -> IO (Either String ([Sentence String]))
parseTuba f = do r <- runX (readDocument [] f >>> process)
case r of
[] -> return $ Left "No parse result."
[pr] -> return $ Right pr
_ -> return $ Left "Ambiguous parse result!"
process :: (ArrowXml a) => a XmlTree ([Sentence String])
process = getChildren >>> listA (tag "sentence" >>> listA word >>> arr (\ns -> Sentence ns))
word :: (ArrowXml a) => a XmlTree (Node String)
word = tag "word" >>> getAttrValue "form" >>> arr (\s -> Word s)
-- | Gets the tag with the given name below the node.
tag :: (ArrowXml a) => String -> a XmlTree XmlTree
tag s = getChildren >>> isElem >>> hasName s
Я пытаюсь прочитать файл корпуса, и структура, очевидно, похожа на <corpus><sentence><word form="Hello"/><word form="world"/></sentence></corpus>
.
Даже на очень маленьком корпусе разработки программасчитывание занимает ~ 15 секунд, из которых около 20% - это время GC (это слишком много).
В частности, много данных тратят слишком много времени в состоянии DRAG.Это профиль:
![http://imgur.com/YC3jh](https://i.stack.imgur.com/PyEVq.png)
мониторинг преступников DRAG.Вы можете видеть, что decodeDocument часто вызывается, и его данные затем останавливаются до самого конца выполнения.
Теперь, я думаю, это легко исправить, сложив все эти вещи decodeDocument в мои структуры данных (Sentence
и Word
) и тогда РТ может забыть об этих громах.Однако в настоящее время происходит то, что свертывание происходит в очень end , когда я форсирую вычисление деконструкцией Either
в монаде IO
, где это может легко произойти онлайн .Я не вижу причин для этого, и мои попытки ужесточить программу до сих пор были тщетными.Я надеюсь, что кто-нибудь может мне помочь: -)
Я просто не могу даже найти слишком много мест, чтобы положить seq
с и $!
с в ...