Quindi, ho giocato con diverse librerie XML Haskell, incluso hexpat e xml-enumerator. Dopo aver letto il capitolo di IO in Real World Haskell (http://book.realworldhaskell.org/read/io.html) ho avuto l'impressione che se avessi eseguito il seguente codice, esso verrà raccolto dopo che l'ho passato.Haskell analizza un grande file xml con poca memoria
Tuttavia, quando lo eseguo su un file di grandi dimensioni, l'utilizzo della memoria continua a salire mentre scorre.
runghc parse.hs bigfile.xml
Cosa sto sbagliando? La mia ipotesi è sbagliata? La mappa/filtro la forza per valutare tutto?
import qualified Data.ByteString.Lazy as BSL
import qualified Data.ByteString.Lazy.UTF8 as U
import Prelude hiding (readFile)
import Text.XML.Expat.SAX
import System.Environment (getArgs)
main :: IO()
main = do
args <- getArgs
contents <- BSL.readFile (head args)
-- putStrLn $ U.toString contents
let events = parse defaultParseOptions contents
mapM_ print $ map getTMSId $ filter isEvent events
isEvent :: SAXEvent String String -> Bool
isEvent (StartElement "event" as) = True
isEvent _ = False
getTMSId :: SAXEvent String String -> Maybe String
getTMSId (StartElement _ as) = lookup "TMSId" as
Il mio obiettivo finale è analizzare un enorme file xml con una semplice interfaccia sax. Non voglio essere a conoscenza dell'intera struttura per essere informato che ho trovato un "evento".
Hai questo comportamento anche quando lo compilo piuttosto che eseguirlo in modalità interpretata? – hammar
E non dimenticare di usare l'ottimizzazione (-O2) durante la compilazione. –
Devi compilare e ottimizzare per portarlo alla raccolta dei rifiuti? Se è così, in futuro cercherò di provarlo. –