尝试读取Word8
的二进制文件,我有以下程序:
import qualified Data.Binary as B
type Chars = [B.Word8]
printChars :: Chars -> IO()
printChars cs = mapM_ print cs
main :: IO()
main = do
chars <- B.decodeFile "chars"
printChars chars
当我运行它时,我收到一个错误:
$ ./test
test: too few bytes. Failed reading at byte position 241
似乎decodeFile
期待无限列表。
我怎么能告诉它只读尽可能多的元素?
编辑:
以下是我正在寻找的代码:(这适用于任何类型,而不仅仅是Word8。)
import Prelude hiding ( readFile )
import Data.ByteString.Lazy ( readFile )
import Data.Binary.Get ( isEmpty, runGet )
import qualified Data.Binary as B
type Chars = [B.Word8]
printChars :: Chars -> IO()
printChars cs = mapM_ print cs
-- see http://hackage.haskell.org/package/binary-0.7.1.0/docs/Data-Binary-Get.html
-- function getTrades
getChars = do
e <- isEmpty
if e then return []
else do
c <- B.get
cs <- getChars
return (c:cs)
main :: IO()
main = do
input <- readFile "chars"
printChars $ runGet getChars input
答案 0 :(得分:4)
Data.Binary
用于以规范方式(由Binary
类实例定义)序列化已知类型。通常,它不适用于非结构化数据。
在您提供给我们的情况下,您尝试将文件中的字节反序列化为[B.Word8]类型的对象。如果您查看Data.Binary
源代码,则可以看到以下内容
instance Binary a => Binary [a] where
get = do n <- get :: Get Int
getMany n
这基本上意味着数组存储如下
[length of array, val1, val2, ....]
因此,当您将值应用于文件时,它会读取文件中的第一个Int(毫无疑问,这是一个非常大的数字),然后尝试读取该数量的值。
如果您只想将文件作为字节加载,则应使用Data.ByteString.getContents