import qualified Data.ByteString.Lazy.Char8 as BS
stuff <- BS.readFile "stuff.txt"
バイト文字列から特定の文字を取得し、その ASCII を変更して元に戻すにはどうすればよいですか? readInt などを使用しますか?
例: "aaaaa" ,"a" は 97 なのでマイナス 1 で "aa`aa" となります
import qualified Data.ByteString.Lazy.Char8 as BS
stuff <- BS.readFile "stuff.txt"
バイト文字列から特定の文字を取得し、その ASCII を変更して元に戻すにはどうすればよいですか? readInt などを使用しますか?
例: "aaaaa" ,"a" は 97 なのでマイナス 1 で "aa`aa" となります
どうBS.map predですか?fromEnumとを使用して、sへのtoEnum/からの変換を行うこともできますInt。
他の人がバイト操作を行う問題に取り組んでいるので、質問の残りの半分に焦点を当てます: 内の特定のバイトを選択して更新しますByteString。より使い慣れたインターフェイスを使用して、単純なリストの操作を実装することから始めましょう。
onNth :: Int -> (a -> a) -> ([a] -> [a])
onNth n f xs = case splitAt n xs of
(beginning, x:ending) -> beginning ++ f x : ending
_ -> xs -- happens when n is out-of-bounds
の代わりにtakeandを使用して、これを同等に実装できます。では、これをsで動作するように変換するにはどうすればよいでしょうか。さて、インターフェイスは、、、、、および;を提供します。まだ入手できていない唯一のものは、上記の部分で行ったパターン マッチングです。幸いなことに、似たようなものを提供しています:dropsplitAtByteStringByteStringtakedropsplitAtappendconsx:endingByteString
uncons :: ByteString -> Maybe (Word8, ByteString)
したがって、それを使用して、sonNthに対して機能する新しい関数を作成できます。ByteString
second :: (b -> c) -> (a, b) -> (a, c)
second f (a, b) = (a, f b)
onNth :: Int -> (Word8 -> Word8) -> (ByteString -> ByteString)
onNth n f bs = case second uncons (splitAt n bs) of
(beginning, Just (x, ending)) -> append beginning (cons (f x) ending)
_ -> bs -- again, for out-of-bounds cases
f :: Word8 -> Word8最後に、上記の引数として使用する関数について説明します。ByteString上記でテキストについて話しましたが、とにかくテキストに使用するべきではないことを指摘します( ByteStrings はバイトのシーケンスであり、 のシーケンスではありませんChar)。したがって、 を使用することを選択した場合はByteString、テキストではなくバイトについて話している必要があります。;-)
したがって、おそらく境界でラップアラウンドして、バイトを1つずつ減らす関数について本当に質問するつもりでした。subtract 1はまさにそれを行う関数なので、 に変換するpack [97, 97, 97, 97, 97]にpack [97, 97, 96, 97, 97]は、 と書くかもしれませんonNth 2 (subtract 1)。読み方はほぼ英語!
を使用してバイトをCharsに変換したらBS.unpack、を使用してfromEnum :: Char -> Int(または、同等にordfromからData.Char)ASCII値に変換しChar、通常の整数のように操作できます。ASCII値をIntバックからに変換するには、またはCharを使用します。その後、sをwithまたは同様のものに変換し直すことができます。toEnumData.Char.chrCharByteStringBS.pack