1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

[Haskell] Strict ByteString の作り方 まとめ

Last updated at Posted at 2023-10-01

Lazy ByteString および ShortByteString については別記事にしました。

参考「[Haskell] Lazy ByteString の作り方 まとめ - Qiita
参考「[Haskell] ShortByteString の作り方 まとめ - Qiita

各関数の説明等は公式ドキュメント等を参照。

参考「Data.ByteString
参考「Data.ByteString.Builder
参考「Data.ByteString.Char8

Builder から直接作れる ByteString は Lazy ByteString のみです。

1. [Word8] または Word8 から作る場合

import qualified Data.ByteString as BS
import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    let byteStringA = BS.pack [99, 97, 116, 32, 227, 129, 173, 227, 129, 147]
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = BS.singleton 99
    BSC.putStrLn byteStringB
    print byteStringB

    let byteStringC = BSC.toStrict . BSB.toLazyByteString . BSB.word8 $ 99
    BSC.putStrLn byteStringC
    print byteStringC
実行結果
cat ねこ
"cat \227\129\173\227\129\147"
c
"c"
c
"c"

2. String = [Char] または Char から作る場合

2.1. 言語拡張を使わない場合

2.1.1. ASCII の場合

import Data.String (fromString)

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    let byteStringA = BSC.pack "cat"
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = fromString "cat"
    BSC.putStrLn byteStringB
    print byteStringB

    let byteStringC = BSC.singleton 'c'
    BSC.putStrLn byteStringC
    print byteStringC

    let byteStringD = BSC.toStrict . BSB.toLazyByteString . BSB.string7 $ "cat"
    BSC.putStrLn byteStringD
    print byteStringD

    let byteStringE = BSC.toStrict . BSB.toLazyByteString . BSB.char7 $ 'c'
    BSC.putStrLn byteStringE
    print byteStringE
実行結果
cat
"cat"
cat
"cat"
c
"c"
cat
"cat"
c
"c"

2.1.2. UTF-8 の場合

やり方によっては UTF-8 を正しく扱えないため注意が必要です。

import Data.String (fromString)

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    -- UTF-8 を正しく扱えない
    let byteStringA = BSC.pack "cat ねこ"
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = fromString "cat ねこ"
    BSC.putStrLn byteStringB
    print byteStringB

    let byteStringC = BSC.singleton 'ね'
    BSC.putStrLn byteStringC
    print byteStringC

    -- UTF-8 を正しく扱える
    let byteStringD = BSC.toStrict . BSB.toLazyByteString . BSB.stringUtf8 $ "cat ねこ"
    BSC.putStrLn byteStringD
    print byteStringD

    let byteStringE = BSC.toStrict . BSB.toLazyByteString . fromString $ "cat ねこ"
    BSC.putStrLn byteStringE
    print byteStringE

    let byteStringF = BSC.toStrict . BSB.toLazyByteString . BSB.charUtf8 $ 'ね'
    BSC.putStrLn byteStringF
    print byteStringF
実行結果
cat mS
"cat mS"
cat mS
"cat mS"
m
"m"
cat ねこ
"cat \227\129\173\227\129\147"
cat ねこ
"cat \227\129\173\227\129\147"
ね
"\227\129\173"

ByteStringfromStringString 型の文字列を UTF-8 として扱いませんが、BuilderfromStringString 型の文字列を UTF-8 として扱います。

2.2. OverloadedStrings 言語拡張を使う場合

2.2.1. ASCII の場合

{-# LANGUAGE OverloadedStrings #-}

import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    let byteString = "cat"
    BSC.putStrLn byteString
    print byteString
実行結果
cat
"cat"

2.2.2. UTF-8 の場合

やり方によっては UTF-8 を正しく扱えないため注意が必要です。

{-# LANGUAGE OverloadedStrings #-}

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    -- UTF-8 を正しく扱えない
    let byteStringA = "cat ねこ"
    BSC.putStrLn byteStringA
    print byteStringA

    -- UTF-8 を正しく扱える
    let byteStringB = BSC.toStrict . BSB.toLazyByteString $ "cat ねこ"
    BSC.putStrLn byteStringB
    print byteStringB
実行結果
cat mS
"cat mS"
cat ねこ
"cat \227\129\173\227\129\147"

ByteString の場合は String 型の文字列を UTF-8 として扱いませんが、Builder の場合は String 型の文字列を UTF-8 として扱います。

3. Lazy ByteString または ShortByteString から作る場合

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC
import qualified Data.ByteString.Lazy as BSL
import qualified Data.ByteString.Short as BSS

main :: IO ()
main = do

    -- 
    let lazyByteString = BSL.pack [99, 97, 116, 32, 227, 129, 173, 227, 129, 147]

    let byteStringA = BSC.toStrict lazyByteString
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = BSC.toStrict . BSB.toLazyByteString . BSB.lazyByteString $ lazyByteString
    BSC.putStrLn byteStringB
    print byteStringB

    -- 
    let shortByteString = BSS.pack [99, 97, 116, 32, 227, 129, 173, 227, 129, 147]

    let byteStringC = BSS.fromShort shortByteString
    BSC.putStrLn byteStringC
    print byteStringC

    let byteStringD = BSC.toStrict . BSB.toLazyByteString . BSB.shortByteString $ shortByteString
    BSC.putStrLn byteStringD
    print byteStringD
実行結果
cat ねこ
"cat \227\129\173\227\129\147"
cat ねこ
"cat \227\129\173\227\129\147"
cat ねこ
"cat \227\129\173\227\129\147"
cat ねこ
"cat \227\129\173\227\129\147"

参考「fromShort - Data.ByteString.Short

4. 空文字列の場合

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    let byteStringA = BSC.empty
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = mempty
    BSC.putStrLn byteStringB
    print byteStringB

    let byteStringC = BSC.toStrict . BSB.toLazyByteString $ mempty
    BSC.putStrLn byteStringC
    print byteStringC
実行結果

""

""

""

5. その他の型から作る場合

他にも様々な型の値から Strict ByteString を作ることができます。

ここでは例として一部のみ載せます。他の作り方に関しては公式ドキュメント等を参照して下さい。

参考「Data.ByteString
参考「Data.ByteString.Builder
参考「Data.ByteString.Char8

import qualified Data.ByteString.Builder as BSB
import qualified Data.ByteString.Char8 as BSC

main :: IO ()
main = do

    let byteStringA = BSC.toStrict . BSB.toLazyByteString . BSB.word32BE $ 0x63617420
    BSC.putStrLn byteStringA
    print byteStringA

    let byteStringB = BSC.toStrict . BSB.toLazyByteString . BSB.byteStringHex $ byteStringA
    BSC.putStrLn byteStringB
    print byteStringB

    let byteStringC = BSC.toStrict . BSB.toLazyByteString . BSB.word32HexFixed $ 0x63617420
    BSC.putStrLn byteStringC
    print byteStringC
実行結果
cat
"cat "
63617420
"63617420"
63617420
"63617420"
1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?