!5-_@      !"#$%&'()*+,-./0123456789:;<=>? None F@ABCDEFGHIJKLM(c) 2020 Andrew LelechenkoBSD3NoneFNONoneF$PbitvecThe number of bits in a Q1. A handy constant to have around when defining Q&-based bulk operations on bit vectors.RbitvecJInsert 0 between each consecutive bits of an input. xyzw --> (x0y0, z0w0)PSTUVWXYZ[\]^_`RabcdNone%27@AFHMV_'bitvec-A newtype wrapper with a custom instance of Data.Vector.UnboxedR, which packs booleans as efficient as possible (8 values per byte). Vectors of % use 8x less memory than vectors of eL (which stores one value per byte). but random writes are up to 20% slower.fbitvec$read a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the result is padded with memory garbage.gbitvec$read a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the result is padded with memory garbage.hbitvecEwrite a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the word is truncated and as many low-order bits as possible are written.bitvecTFlip the bit at the given position. No bounds checks are performed. Equivalent to i  j#, but up to 33% faster and atomic.!In general there is no reason to ) bit vectors: either you modify it with k (which is k altogether) or with j (which is ).EData.Vector.Unboxed.modify (\v -> unsafeFlipBit v 1) (read "[1,1,1]")[1,0,1]bitvec3Flip the bit at the given position. Equivalent to i   j#, but up to 33% faster and atomic.!In general there is no reason to  ) bit vectors: either you modify it with k (which is k altogether) or with j (which is ).?Data.Vector.Unboxed.modify (\v -> flipBit v 1) (read "[1,1,1]")[1,0,1]lbitvecThere is only one lawful m instance possible with n = o and p =  . q.rstuvwfgxh None>SX@ bitvec1Cast a vector of words to a vector of bits. Cf.  .bitveceTry to cast a vector of bits to a vector of words. It succeeds if a vector of bits is aligned. Use  otherwise. Cf.  .bitvecClone a vector of bits to a new unboxed vector of words. If the bits don't completely fill the words, the last word will be zero-padded. Cf.  .ybitvec2Clone a vector of bits to a new unboxed vector of z9. If the bits don't completely fill the words, the last z will be zero-padded. Cf. .bitvecZZip two vectors with the given function. rewriting contents of the second argument. Cf. .import Data.Bits;modify (zipInPlace (.&.) (read "[1,1,0]")) (read "[0,1,1]")[0,1,0]Warningo: if the immutable vector is shorter than the mutable one, it is a caller's responsibility to trim the result:import Data.BitsAmodify (zipInPlace (.&.) (read "[1,1,0]")) (read "[0,1,1,1,1,1]")&[0,1,0,1,1,1] -- note trailing garbage bitvec Invert (flip) all bits in-place.=Data.Vector.Unboxed.modify invertInPlace (read "[0,1,0,1,0]") [1,0,1,0,1] bitvecSame as , but deposit selected bits in-place. Returns a number of selected bits. It is caller's responsibility to trim the result to this number. bitvecSame as , but deposit excluded bits in-place. Returns a number of excluded bits. It is caller's responsibility to trim the result to this number. bitvec#Reverse the order of bits in-place.>Data.Vector.Unboxed.modify reverseInPlace (read "[1,1,0,1,0]") [0,1,0,1,1]Consider using  vector-rotcev* package to reverse vectors in O(1) time. y None%27@AFHMV__ bitvec-A newtype wrapper with a custom instance of Data.Vector.UnboxedR, which packs booleans as efficient as possible (8 values per byte). Vectors of  % use 8x less memory than vectors of eL (which stores one value per byte). but random writes are up to 10% slower.{bitvec$read a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the result is padded with memory garbage.|bitvec$read a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the result is padded with memory garbage.}bitvecEwrite a word at the given bit offset in little-endian order (i.e., the LSB will correspond to the bit at the given address, the 2's bit will correspond to the address + 1, etc.). If the offset is such that the word extends past the end of the vector, the word is truncated and as many low-order bits as possible are written.bitvecTFlip the bit at the given position. No bounds checks are performed. Equivalent to i  j, but up to 2x faster.!In general there is no reason to ) bit vectors: either you modify it with k (which is k altogether) or with j (which is ).EData.Vector.Unboxed.modify (\v -> unsafeFlipBit v 1) (read "[1,1,1]")[1,0,1]bitvec3Flip the bit at the given position. Equivalent to i   j, but up to 2x faster.!In general there is no reason to  ) bit vectors: either you modify it with k (which is k altogether) or with j (which is ).?Data.Vector.Unboxed.modify (\v -> flipBit v 1) (read "[1,1,1]")[1,0,1]~bitvecThere is only one lawful m instance possible with n = o and p =   . q.rt {|}None>SXx bitvec1Cast a vector of words to a vector of bits. Cf.  .bitveceTry to cast a vector of bits to a vector of words. It succeeds if a vector of bits is aligned. Use  otherwise. Cf.  .bitvecClone a vector of bits to a new unboxed vector of words. If the bits don't completely fill the words, the last word will be zero-padded. Cf.  .bitvec2Clone a vector of bits to a new unboxed vector of z9. If the bits don't completely fill the words, the last z will be zero-padded. Cf. .bitvecZZip two vectors with the given function. rewriting contents of the second argument. Cf. .import Data.Bits;modify (zipInPlace (.&.) (read "[1,1,0]")) (read "[0,1,1]")[0,1,0]Warningo: if the immutable vector is shorter than the mutable one, it is a caller's responsibility to trim the result:import Data.BitsAmodify (zipInPlace (.&.) (read "[1,1,0]")) (read "[0,1,1,1,1,1]")&[0,1,0,1,1,1] -- note trailing garbagebitvec Invert (flip) all bits in-place.=Data.Vector.Unboxed.modify invertInPlace (read "[0,1,0,1,0]") [1,0,1,0,1]bitvecSame as , but deposit selected bits in-place. Returns a number of selected bits. It is caller's responsibility to trim the result to this number.bitvecSame as , but deposit excluded bits in-place. Returns a number of excluded bits. It is caller's responsibility to trim the result to this number.bitvec#Reverse the order of bits in-place.>Data.Vector.Unboxed.modify reverseInPlace (read "[1,1,0,1,0]") [0,1,0,1,1]Consider using  vector-rotcev* package to reverse vectors in O(1) time. None=>?SXbitvecDCast an unboxed vector of words to an unboxed vector of bits. Cf. .1castFromWords (Data.Vector.Unboxed.singleton 123)[1,1,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0]bitvecxTry to cast an unboxed vector of bits to an unboxed vector of words. It succeeds if a vector of bits is aligned. Use  otherwise. Cf. .'castToWords (castFromWords v) == Just vbitvecClone an unboxed vector of bits to a new unboxed vector of words. If the bits don't completely fill the words, the last word will be zero-padded. Cf. .'cloneToWords (read "[1,1,0,1,1,1,1,0]")[123]bitvecCast a unboxed vector of zG to an unboxed vector of bits. This can be used in conjunction with bytestring-to-vector package to convert from ::set -XOverloadedStrings&import Data.Vector.Storable.ByteString?castFromWords8 (Data.Vector.convert (byteStringToVector "abc"))1[1,0,0,0,0,1,1,0,0,1,0,0,0,1,1,0,1,1,0,0,0,1,1,0]bitvec?Try to cast an unboxed vector of bits to an unboxed vector of z4. It succeeds if a vector of bits is aligned. Use  otherwise.)castToWords8 (castFromWords8 v) == Just vbitvec<Clone an unboxed vector of bits to a new unboxed vector of z:. If the bits don't completely fill the words, the last z= will be zero-padded. This can be used in conjunction with bytestring-to-vector package to convert to ::set -XOverloadedLists&import Data.Vector.Storable.ByteStringovectorToByteString (Data.Vector.convert (Data.Bit.cloneToWords8 [1,0,0,0,0,1,1,0,0,1,0,0,0,1,1,0,1,1,0,0,0,1]))"ab#" bitvec5Zip two vectors with the given function. Similar to , but up to 1000x (!) faster.6For sufficiently dense sets, represented as bitmaps,   is up to 32x faster than , , etc.import Data.Bits?zipBits (.&.) (read "[1,1,0]") (read "[0,1,1]") -- intersection[0,1,0]8zipBits (.|.) (read "[1,1,0]") (read "[0,1,1]") -- union[1,1,1]TzipBits (\x y -> x .&. complement y) (read "[1,1,0]") (read "[0,1,1]") -- difference[1,0,0]EzipBits xor (read "[1,1,0]") (read "[0,1,1]") -- symmetric difference[1,0,1]!bitvecInvert (flip) all bits.invertBits (read "[0,1,0,1,0]") [1,0,1,0,1]"bitvecFor each set bit of the first argument, deposit the corresponding bit of the second argument to the result. Similar to the parallel deposit instruction (PDEP).4selectBits (read "[0,1,0,1,1]") (read "[1,1,0,0,1]")[1,0,1].Here is a reference (but slow) implementation: rimport qualified Data.Vector.Unboxed as U selectBits mask ws == U.map snd (U.filter (unBit . fst) (U.zip mask ws))#bitvecoFor each unset bit of the first argument, deposit the corresponding bit of the second argument to the result.5excludeBits (read "[0,1,0,1,1]") (read "[1,1,0,0,1]")[1,0].Here is a reference (but slow) implementation: yimport qualified Data.Vector.Unboxed as U excludeBits mask ws == U.map snd (U.filter (not . unBit . fst) (U.zip mask ws))$bitvecReverse the order of bits. reverseBits (read "[1,1,0,1,0]") [0,1,0,1,1]Consider using  vector-rotcev* package to reverse vectors in O(1) time.%bitvec_Return the index of the first bit in the vector with the specified value, if any. Similar to , but up to 64x faster.(bitIndex (Bit True) (read "[0,0,1,0,1]")Just 2(bitIndex (Bit True) (read "[0,0,0,0,0]")Nothing!bitIndex bit == nthBitIndex bit 1GOne can also use it to reduce a vector with disjunction or conjunction:import Data.Maybe/isAnyBitSet = isJust . bitIndex (Bit True)0areAllBitsSet = isNothing . bitIndex (Bit False)&bitvecReturn the index of the n?-th bit in the vector with the specified value, if any. Here n4 is 1-based and the index is 0-based. Non-positive n results in an error.1nthBitIndex (Bit True) 2 (read "[0,1,0,1,1,1,0]")Just 31nthBitIndex (Bit True) 5 (read "[0,1,0,1,1,1,0]")Nothing One can use & to implement to implement  select{0,1} queries for  5https://en.wikipedia.org/wiki/Succinct_data_structuresuccinct dictionaries.'bitvecGReturn the number of set bits in a vector (population count, popcount). countBits (read "[1,1,0,1,0,1]")4One can combine ' with   to implement  rank{0,1} queries for  5https://en.wikipedia.org/wiki/Succinct_data_structuresuccinct dictionaries.(bitvec+Return the indices of set bits in a vector.listBits (read "[1,1,0,1,0,1]") [0,1,3,5] !"#$%&'(!None=>?SX)bitvecDCast an unboxed vector of words to an unboxed vector of bits. Cf. .1castFromWords (Data.Vector.Unboxed.singleton 123)[1,1,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0]*bitvecxTry to cast an unboxed vector of bits to an unboxed vector of words. It succeeds if a vector of bits is aligned. Use + otherwise. Cf. .'castToWords (castFromWords v) == Just v+bitvecClone an unboxed vector of bits to a new unboxed vector of words. If the bits don't completely fill the words, the last word will be zero-padded. Cf. .'cloneToWords (read "[1,1,0,1,1,1,1,0]")[123],bitvecCast a unboxed vector of zG to an unboxed vector of bits. This can be used in conjunction with bytestring-to-vector package to convert from ::set -XOverloadedStrings&import Data.Vector.Storable.ByteString?castFromWords8 (Data.Vector.convert (byteStringToVector "abc"))1[1,0,0,0,0,1,1,0,0,1,0,0,0,1,1,0,1,1,0,0,0,1,1,0]-bitvec?Try to cast an unboxed vector of bits to an unboxed vector of z4. It succeeds if a vector of bits is aligned. Use  otherwise.)castToWords8 (castFromWords8 v) == Just v.bitvec<Clone an unboxed vector of bits to a new unboxed vector of z:. If the bits don't completely fill the words, the last z= will be zero-padded. This can be used in conjunction with bytestring-to-vector package to convert to ::set -XOverloadedLists&import Data.Vector.Storable.ByteStringovectorToByteString (Data.Vector.convert (Data.Bit.cloneToWords8 [1,0,0,0,0,1,1,0,0,1,0,0,0,1,1,0,1,1,0,0,0,1]))"ab#"/bitvec5Zip two vectors with the given function. Similar to , but up to 1000x (!) faster.6For sufficiently dense sets, represented as bitmaps, / is up to 32x faster than , , etc.import Data.Bits?zipBits (.&.) (read "[1,1,0]") (read "[0,1,1]") -- intersection[0,1,0]8zipBits (.|.) (read "[1,1,0]") (read "[0,1,1]") -- union[1,1,1]TzipBits (\x y -> x .&. complement y) (read "[1,1,0]") (read "[0,1,1]") -- difference[1,0,0]EzipBits xor (read "[1,1,0]") (read "[0,1,1]") -- symmetric difference[1,0,1]0bitvecInvert (flip) all bits.invertBits (read "[0,1,0,1,0]") [1,0,1,0,1]1bitvecFor each set bit of the first argument, deposit the corresponding bit of the second argument to the result. Similar to the parallel deposit instruction (PDEP).4selectBits (read "[0,1,0,1,1]") (read "[1,1,0,0,1]")[1,0,1].Here is a reference (but slow) implementation: rimport qualified Data.Vector.Unboxed as U selectBits mask ws == U.map snd (U.filter (unBit . fst) (U.zip mask ws))2bitvecoFor each unset bit of the first argument, deposit the corresponding bit of the second argument to the result.5excludeBits (read "[0,1,0,1,1]") (read "[1,1,0,0,1]")[1,0].Here is a reference (but slow) implementation: yimport qualified Data.Vector.Unboxed as U excludeBits mask ws == U.map snd (U.filter (not . unBit . fst) (U.zip mask ws))3bitvecReverse the order of bits. reverseBits (read "[1,1,0,1,0]") [0,1,0,1,1]Consider using  vector-rotcev* package to reverse vectors in O(1) time.4bitvec_Return the index of the first bit in the vector with the specified value, if any. Similar to , but up to 64x faster.(bitIndex (Bit True) (read "[0,0,1,0,1]")Just 2(bitIndex (Bit True) (read "[0,0,0,0,0]")Nothing!bitIndex bit == nthBitIndex bit 1GOne can also use it to reduce a vector with disjunction or conjunction:import Data.Maybe/isAnyBitSet = isJust . bitIndex (Bit True)0areAllBitsSet = isNothing . bitIndex (Bit False)5bitvecReturn the index of the n?-th bit in the vector with the specified value, if any. Here n4 is 1-based and the index is 0-based. Non-positive n results in an error.1nthBitIndex (Bit True) 2 (read "[0,1,0,1,1,1,0]")Just 31nthBitIndex (Bit True) 5 (read "[0,1,0,1,1,1,0]")Nothing One can use 5 to implement to implement  select{0,1} queries for  5https://en.wikipedia.org/wiki/Succinct_data_structuresuccinct dictionaries.6bitvecGReturn the number of set bits in a vector (population count, popcount). countBits (read "[1,1,0,1,0,1]")4One can combine 6 with   to implement  rank{0,1} queries for  5https://en.wikipedia.org/wiki/Succinct_data_structuresuccinct dictionaries.7bitvec+Return the indices of set bits in a vector.listBits (read "[1,1,0,1,0,1]") [0,1,3,5])*+,-./01234567"None 27FMSX_Z 8bitvec:Binary polynomials of one variable, backed by an unboxed # .EPolynomials are stored normalized, without leading zero coefficients.W instance does not make much sense mathematically, it is defined only for the sake of $%, &', etc.:set -XBinaryLiterals*-- (1 + x) (1 + x + x^2) = 1 + x^3 (mod 2)0b11 * 0b111 :: F2Poly0b10019bitvecConvert 8M to a vector of coefficients (first element corresponds to a constant term).:bitvecMake 8M from a list of coefficients (first element corresponds to a constant term).bitvecValid 8& has offset 0 and no trailing garbage.bitvecNInputs must be valid for wrapping into F2Poly: no trailing garbage is allowed.bitvecMust be >= 2 * wordSize.;bitvec;Execute the extended Euclidean algorithm. For polynomials a and b/, compute their unique greatest common divisor g( and the unique coefficient polynomial s satisfying  as + bt = g.:set -XBinaryLiteralsgcdExt 0b101 0b0101 (0b101,0b0)gcdExt 0b11 0b111 (0b1,0b10)bitvec* converts a binary polynomial, encoded as 8, to  encoding.bitvec3Addition and multiplication are evaluated modulo 2. = k and  =  1.p* converts a binary polynomial, encoded as , to 8 encoding.89:;0(c) 2019 Andrew Lelechenko, 2012-2016 James CookBSD3/Andrew Lelechenko <andrew.lelechenko@gmail.com>None8   !"#$%&'(89:;  !$%&'("# 89:;(None 27FMSX_*} <bitvec:Binary polynomials of one variable, backed by an unboxed #  .EPolynomials are stored normalized, without leading zero coefficients.W instance does not make much sense mathematically, it is defined only for the sake of $%, &', etc.:set -XBinaryLiterals*-- (1 + x) (1 + x + x^2) = 1 + x^3 (mod 2)0b11 * 0b111 :: F2Poly0b1001=bitvecConvert <M to a vector of coefficients (first element corresponds to a constant term).>bitvecMake <M from a list of coefficients (first element corresponds to a constant term).bitvecValid <& has offset 0 and no trailing garbage.bitvecNInputs must be valid for wrapping into F2Poly: no trailing garbage is allowed.bitvecMust be >= 2 * wordSize.?bitvec;Execute the extended Euclidean algorithm. For polynomials a and b/, compute their unique greatest common divisor g( and the unique coefficient polynomial s satisfying  as + bt = g.:set -XBinaryLiteralsgcdExt 0b101 0b0101 (0b101,0b0)gcdExt 0b11 0b111 (0b1,0b10)bitvec* converts a binary polynomial, encoded as <, to  encoding.bitvec3Addition and multiplication are evaluated modulo 2. = k and  =  1.p* converts a binary polynomial, encoded as , to < encoding.<=>?0(c) 2019 Andrew Lelechenko, 2012-2016 James CookBSD3/Andrew Lelechenko <andrew.lelechenko@gmail.com>None,[ )*+,-./01234567<=>? )*+,-./03456712<=>?))*+,    - . / 0 1))*+,-./01   23456789! ! ! !2!3!!!4!!!5!6!7!8!9":";"<"=(:(;(<(=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdOPefghijkilmijnoipqiprilsiptiuvwxyzwx#{||} ~ifghoz{||}~O""""iu"ipipij(((((%bitvec-1.0.3.0-6Y7CZlWHu4X4leNYPAYtDiData.Bit.ThreadSafeData.Bit Data.Bit.GmpData.Bit.PdepPextData.Bit.UtilsData.Bit.InternalTSData.Vector.Unboxed.Mutable unsafeModifymodifyData.Bit.MutableTS castFromWords castToWords cloneToWords cloneToWords8zipBits selectBits excludeBitsData.Bit.InternalData.Bit.MutableData.Bit.ImmutableTScastFromWordsM castToWordsM cloneToWordsMData.ByteString ByteStringData.Vector.UnboxedzipWith Data.IntSetunion intersection elemIndextakeData.Bit.ImmutableData.Bit.F2PolyTSVectorData.SetSetData.MapMapData.Bit.F2PolyBitunBit unsafeFlipBitflipBit zipInPlace invertInPlaceselectBitsInPlaceexcludeBitsInPlacereverseInPlacecastFromWords8 castToWords8 invertBits reverseBitsbitIndex nthBitIndex countBitslistBitsF2PolyunF2PolytoF2PolygcdExtmpnCom mpnLshift mpnRshiftmpnScan0mpnScan1 mpnPopcountmpnAndNmpnIorNmpnXorNmpnAndnNmpnIornNmpnNandNmpnNiorNmpnXnorNpdeppextwordSizeghc-prim GHC.TypesWord sparseBits lgWordSize divWordSize modWordSize mulWordSizenWords wordsToBytesalignedalignUpmaskedmeld reverseWordreversePartialWordffs selectWordloMaskhiMaskfromPrimVector toPrimVectorBool indexWordreadWord writeWordbaseGHC.Baseflip Data.Bits complementid$fNumBitGHC.NumNum+xor fromIntegerGHC.Realodd&vector-0.12.1.2-E9YBdJZ4ywF23gc9L8wAxpData.Vector.Unboxed.BaseMVectorBitMVecBitVec WithInternalsmodifyByteArraycloneToWords8MGHC.WordWord8 GHC.ClassesOrd_isValidxorBitskaratsubaThreshold$fIntegralF2Poly toInteger integer-gmpGHC.Integer.TypeInteger $fNumF2Polyabssignumconst