文本或字节串

美好的一天。

我现在讨厌Haskell的一件事是与string一起工作的包的数量。

首先,我使用本机Haskell [Char]string,但是当我试图开始使用hackage库时,完全失去了无尽的转换。 每个包似乎都使用不同的string实现,有的采用自己手工制作的东西。

接下来,我用Data.Textstring和OverloadedStrings扩展名重写了我的代码,我select了Text因为它具有更广泛的function集,但是似乎很多项目都喜欢ByteString
有人可以给出简短的推理,为什么要使用一个或其他?

PS:顺便说一句如何从Text转换为ByteString

无法匹配预期的typesData.ByteString.Lazy.Internal.ByteString针对推断的typesText Expected type:IO Data.ByteString.Lazy.Internal.ByteString推断的types:IO Text

我试图从Data.Text.Encoding ,但没有运气:

无法匹配预期的typesData.ByteString.Lazy.Internal.ByteString对于推断的typesData.ByteString.Internal.ByteString

UPD:

感谢您的回应,那*大块的善良看起来像路要走,但我有点震惊的结果,我原来的function是这样的:

 htmlToItems :: Text -> [Item] htmlToItems = getItems . parseTags . convertFuzzy Discard "CP1251" "UTF8" 

现在成了:

 htmlToItems :: Text -> [Item] htmlToItems = getItems . parseTags . fromLazyBS . convertFuzzy Discard "CP1251" "UTF8" . toLazyBS where toLazyBS t = fromChunks [encodeUtf8 t] fromLazyBS t = decodeUtf8 $ intercalate "" $ toChunks t 

是的,这个function是不行的,因为它的错误,如果我们提供的Text ,那么我们有信心这个文本是正确的编码和准备使用和转换它是愚蠢的事情要做,但如此详细的转换仍然发生在htmltoItems之外的htmltoItems

ByteStrings主要用于二进制数据,但如果您只需要ASCII字符集,它们也是一种处理文本的有效方法。 如果你需要处理Unicodestring,你需要使用Text 。 然而,我必须强调的是,这两者都不是替代,它们通常用于不同的事情:虽然Text表示纯粹的Unicode,你仍然需要编码二进制ByteString表示,无论何时,例如通过套接字或传输文本文件。

这里是一个关于unicode的基础知识的好文章,它解释unicode代码点( Text )和编码的二进制字节( ByteString )的关系是一个体面的工作: 绝对最小每个软件开发人员绝对,积极必须知道Unicode和字符集

你可以使用Data.Text.Encoding模块在两个数据types之间进行转换,如果你正在使用懒惰变体(就像你正在根据你的错误信息所做的那样),你可以使用Data.Text.Lazy.Encoding进行转换。

你一定想使用Data.Text作为文本数据。

encodeUtf8是要走的路。 这个错误:

无法匹配预期的typesData.ByteString.Lazy.Internal.ByteString对于推断的typesData.ByteString.Internal.ByteString

意味着你正在提供一个严格的字节串来代码,它需要一个懒惰的字节串。 使用fromChunks函数进行转换很简单:

 Data.ByteString.Lazy.fromChunks :: [Data.ByteString.Internal.ByteString] -> ByteString 

所以你需要做的就是在需要延迟字节fromChunks [myStrictByteString]地方添加函数fromChunks [myStrictByteString]

另一种方式的转换可以用双重函数toChunks来完成,它使用一个懒惰的string并给出一个严格的块的列表。

你可能想问一些包的维护者,如果他们能够提供一个文本接口而不是string接口,或者除了string接口。

使用Data.String.Conversions的单个函数cs

它将允许您根据input和预期types在StringByteString StringText (以及ByteString.LazyText.Lazy )之间进行转换。

你仍然需要调用它,但不再担心各自的types。

查看这个答案的用法示例。