readFile "file.html"
"start of the file... *** Exception: file.html: hGetContents: invalid argument (invalid code page byte sequence)
これはnotepad ++で作成されたUTF-8ファイルです...どのようにしてhaskellでファイルを読むことができますか?haskell - 無効なコードページのバイトシーケンス
readFile "file.html"
"start of the file... *** Exception: file.html: hGetContents: invalid argument (invalid code page byte sequence)
これはnotepad ++で作成されたUTF-8ファイルです...どのようにしてhaskellでファイルを読むことができますか?haskell - 無効なコードページのバイトシーケンス
デフォルトでは、ファイルはシステムロケールで読み込まれるため、非標準のエンコーディングを使用するファイルがある場合は、ファイルハンドルのエンコーディングを自分で設定する必要があります。
foo = do
handle <- openFile "file.html" ReadMode
hSetEncoding handle utf8_bom
contents <- hGetContents handle
doSomethingWithContents
hClose handle
をご利用ください。これは何のエラー処理が含まれていない、より良い方法は、このようにthis siteによる
import Control.Exception -- for bracket
foo = bracket
(openFile "file.html" ReadMode >>= \h -> hSetEncoding h utf8_bom >> return h)
hClose
(\h -> hGetContents h >>= doSomething)
または
foo = withFile "file.html" ReadMode $
\h -> do hSetEncoding h utf8_bom
contents <- hGetContents h
doSomethingWith contents
私は(' foo'のように、 '_bom'について知りませんでしたが)同様のものを考え出しました。 'readFile'で行うように、計算を外部に行うことは可能ですか? 'foo'の例は' hClose'の行を使わないとうまくいきます(そして私のおもちゃのプログラムではOKですが、 "正しい方法"を知りたいのですが) 'IO(String、ハンドル) '?) –
あなたのファイルを遅延読み込みする必要がある場合は、少し難しいです。 'hClose'は計算が戻るときにファイルを閉じます。これはファイルの何かが読み込まれる前に起こるかもしれません。したがって、ファイル全体を一度にメモリに保存することができれば、単純な '' length contents '' seq' return contents''を実行すると、ファイル全体が読み込まれ、処理が外にできます。それ以外の場合は、ファイルを怠惰な 'ByteString'として読み込み、それを' utf8-string'パッケージの 'Data.ByteString.Lazy.UTF8.toString'を使って変換するのが最善でしょう。 –
'ByteString'が物事をより簡単にしてくれます(私は初心者ですが)。' readFile'はレイジーですよね?では、ファイルをどのように閉じるのですか?最後の文字が読み込まれたことをチェックしますか?私はそれを何とか模倣することができますか? –
になり、次のように、あなたの6つのバイトをデコードすることに注意してください:
EF BB BF -> ZERO WIDTH NO-BREAK SPACE (i.e. the BOM, although its not needed in UTF-8
C4 8D -> LATIN SMALL LETTER C WITH CARON (what you said)
0D -> CARRIAGE RETURN (CR)
だから、そのA法的なUTF-8シーケンス。
しかし、標準のPrelude関数はもともとASCIIを行っただけです。私は彼らが今何をしているのか分からないが、いくつかのアイデアについてはこの質問How does GHC/Haskell decide what character encoding it's going to decode/encode from/to?を参照してください。そして、Prelude関数の代わりにhttp://hackage.haskell.org/package/utf8-stringを使用してください。
おそらく、このエラーを示す最小限のファイルの16進ダンプを投稿できますか?私はあなたのエラーを複製することはできません。 – ghoti
この文字を使用してください: 'č' –
あなたのロケールは何ですか?それはutf-8のものか何かucs2ish(notepad ++はWindowsを示唆していますか?)ですか? –