import Data.Char {- Prelude の lines と words lines :: String -> [String] lines "" = [] lines s = let (l,s') = break ('\n'==) s in l : case s' of [] -> [] (_:s'') -> lines s'' words :: String -> [String] words s = case dropWhile Char.isSpace s of "" -> [] s' -> w : words s'' where (w, s'') = break Char.isSpace s' -} -- 区切り子判定述語を与える版の words words2 :: (Char -> Bool) -> String -> [String] words2 p s = case dropWhile isSpace s of "" -> [] s' -> w : words2 p s'' where (w, s'') = case break p s' of (v,_:s'') -> (v,s'') vs -> vs {- words = words2 isSpace -} -- CSV (comma separated values) 形式の文字列を分解する csv :: String -> [String] csv = map trim . words2 (','==) trim :: String -> String -- 文字列後尾の白空白の削除 trim = reverse . dropWhile isSpace . reverse -- 句読点と空白を区切り文字にして分解する wordsInSentence :: String -> [String] wordsInSentence = words2 (`elem` " ,.!?") -- データ塊の開始を表す文字と終了を表す文字との組(のリスト)をパラメータ化 words3 :: [(Char, Char)] -> (Char -> Bool) -> String -> [String] words3 ps p s = case dropWhile isSpace s of "" -> [] ccs@(c:cs) -> case lookup c ps of Nothing -> case break p ccs of (v,"") -> [trim v] (v,_:cs') -> trim v : words3 ps p cs' Just cl -> case break (cl==) cs of (v,"") -> error ("closing '"++cl:"' not foud") (v,_:cs') -> v : words3 ps p cs' -- Apache(HTTP サーバ)ログ行の分解 accessLog :: String -> [String] accessLog = words3 [('[',']'),('"','"')] isSpace