如何在Haskell中将资源编译为二进制文件?

28

假设我有一个 dictionary.txt 文件,我需要将其读入一个映射中并在程序中使用,如何让这个 dictionary.txt 文件包含在编译后的 exe 文件中?

答: 我应该如何将 dictionary.txt 文件嵌入到可执行文件中以便在程序中使用呢?
4个回答

21

文件嵌入是否因其模板而不需要最终用户使用? - alternative
嵌入可执行文件有意义吗? - Stéphane Laurent

15
您可以将序列化的数据类型存储为字节字符串文字。以下是一个示例: 然而,file-embed 自动化了这个过程,使得非平凡嵌入更容易实现。
所有方法本质上都归结为将静态数据表示为字节字符串文字。
{-# LANGUAGE OverloadedStrings #-}

import Data.Binary
import qualified Data.Map as M
import qualified Data.ByteString.Char8 as S
import Data.ByteString.Lazy
import Codec.Compression.GZip

--
-- this is a gzip compressed literal bytestring, storing a binary-encoded Data.Map
--
mytable =
    "\US\139\b\NUL\NUL\NUL\NUL\NUL\NUL\ETXEN\
    \\219\SO\194 \f\197\224\188\196\CAN\227\US\
    \\224\171~\NAKc\GS4ce\161`\178\191\215(\176\
    \\190\180\167\231\210\n\241\171\203\191\ti\
    \\157\217\149\249< \ENQ\214\&9>\202\162\179a\
    \\132X\233\ESC=\231\215\164\SYN\157\DC2D\226*\
    \\146\174o\t\167\DLE\209\"i_\240\193\129\199<W\
    \\250nC\CAN\212\CAN\162J\160\141C\178\133\216;\
    \\\@4\144-W\203\209x\205\140\166\RS\163\237]9f\
    \\170\143\ACK\163g\223\STX\184\&7\rH\222\FSW\
    \\130\&7D\197\NUL\164\&0U\193\186\t\186o\
    \\228\180~\NUL\a6\249\137#\SOH\NUL\NUL"

main = print =<< M.lookup "ghc" m
    where
        -- build the table from the bytestring:
        m :: M.Map String (Maybe String)
        m = decode . decompress . fromChunks . return $ mytable

8

您可以使用自定义的Makefile/Setup.hs钩子,并调用windres(如果您在Windows上)或objcopy/elfrc(如果您在Linux上)将资源编译为COFF/ELF对象,然后将其与Haskell对象文件组合以形成最终可执行文件。然后,您可以像这样(未经测试)使用Haskell FFI访问资源:

-- We have an image resource called "_imgdata"
foreign import ccall "&" _imgdata :: CString 

-- Size of _imgdata is 405585 bytes.
imgdata :: CStringLen
imgdata = (_imgdata, 405585)

这个解决方案比使用 file-embed 更高效(没有进行 CString -> ByteString 转换),但也更加复杂。
另外,我在开发 cabal-install 时还需要资源文件支持 during my work on cabal-install,所以它可能会被集成到某个未来版本的 Cabal 中(如果我实现它)。

7

我强烈建议在这里使用Template Haskell,将文件加载并转换为Haskell数据类型。它不仅会编译到最终的二进制文件中,而且还会完全优化。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接