Wie lese (und analysiere) ich eine Datei und hänge sie dann ohne Ausnahme an dieselbe Datei an?
Ich versuche, in Haskell korrekt aus einer Datei zu lesen, aber es scheint, als ob ich diesen Fehler erhalte.
*** Ausnahme: neo.txt: openFile: resource busy (Datei ist gesperrt) Dies ist mein Code.
import Data.Char
import Prelude
import Data.List
import Text.Printf
import Data.Tuple
import Data.Ord
import Control.Monad
import Control.Applicative((<*))
import Text.Parsec
( Parsec, ParseError, parse -- Types and parser
, between, noneOf, sepBy, many1 -- Combinators
, char, spaces, digit, newline -- Simple parsers
)
Dies sind die Filmfelder.
type Title = String
type Director = String
type Year = Int
type UserRatings = (String,Int)
type Film = (Title, Director, Year , [UserRatings])
type Period = (Year, Year)
type Database = [Film]
Dies ist das Parsen aller Typen, um korrekt aus der Datei zu lesen
-- Parse a string to a string
stringLit :: Parsec String u String
stringLit = between (char '"') (char '"') $ many1 $ noneOf "\"\n"
-- Parse a string to a list of strings
listOfStrings :: Parsec String u [String]
listOfStrings = stringLit `sepBy` (char ',' >> spaces)
-- Parse a string to an int
intLit :: Parsec String u Int
intLit = fmap read $ many1 digit
-- Or `read <-- Parse a string to a string
stringLit :: Parsec String u String
stringLit = between (char '"') (char '"') $ many1 $ noneOf "\"\n"
-- Parse a string to a list of strings
listOfStrings :: Parsec String u [String]
listOfStrings = stringLit `sepBy` (char ',' >> spaces)
-- Parse a string to an int
intLit :: Parsec String u Int
intLit = fmap read $ many1 digit
-- Or `read <$> many1 digit` with Control.Applicative
stringIntTuple :: Parsec String u (String , Int)
stringIntTuple = liftM2 (,) stringLit intLit
film :: Parsec String u Film
film = do
-- alternatively `title <- stringLit <* newline` with Control.Applicative
title <- stringLit
newline
director <- stringLit
newline
year <- intLit
newline
userRatings <- stringIntTuple
newline
return (title, director, year, [userRatings])
films :: Parsec String u [Film]
films = film `sepBy` newline
gt; many1 digit` with Control.Applicative
stringIntTuple :: Parsec String u (String , Int)
stringIntTuple = liftM2 (,) stringLit intLit
film :: Parsec String u Film
film = do
-- alternatively `title <- stringLit <* newline` with Control.Applicative
title <- stringLit
newline
director <- stringLit
newline
year <- intLit
newline
userRatings <- stringIntTuple
newline
return (title, director, year, [userRatings])
films :: Parsec String u [Film]
films = film `sepBy` newline
Dies ist das Hauptprogramm (schreibe "main" in winghci, um das Programm zu starten)
-- The Main
main :: IO ()
main = do
putStr "Enter your Username: "
name <- getLine
filmsDatabase <- loadFile "neo.txt"
appendFile "neo.txt" (show filmsDatabase)
putStrLn "Your changes to the database have been successfully saved."
Dies ist die loadFile-Funktion
loadFile :: FilePath -> IO (Either ParseError [Film])
loadFile filename = do
database <- readFile filename
return $ parse films "Films" database
der andere txt-Dateiname ist neo und enthält einige Filme wie diesen
"Blade Runner"
"Ridley Scott"
1982
("Amy",5), ("Bill",8), ("Ian",7), ("Kevin",9), ("Emma",4), ("Sam",7), ("Megan",4)
"The Fly"
"David Cronenberg"
1986
("Megan",4), ("Fred",7), ("Chris",5), ("Ian",0), ("Amy",6)
Kopieren Sie einfach alles, fügen Sie eine txt-Datei in dasselbe Verzeichnis ein und testen Sie sie, um den von mir beschriebenen Fehler festzustellen.