# BitArray

class BitArray(__auto: BitsType | int | None, length: int | None = None, offset: int | None = None, **kwargs)

  The `Bits` class is the base class for `BitArray` and so (with the exception of `__hash__`) all of its methods are also available for `BitArray` objects. The initialiser is also the same as for `Bits` and so won’t be repeated here.

  A `BitArray` is a mutable `Bits`, and so the one thing all of the methods listed here have in common is that they can modify the contents of the bitstring.

## Methods

BitArray.append(bs: BitsType) → None

  Join a `BitArray` to the end of the current `BitArray`.

      >>> s = BitArray('0xbad')
      >>> s.append('0xf00d')
      >>> s
      BitArray('0xbadf00d')

BitArray.byteswap(fmt: str | int | Iterable[int] | None = None, start: int | None = None, end: int | None = None, repeat: bool = True) → int

  Change the endianness of the `BitArray` in-place according to fmt. Return the number of swaps done.

  The fmt can be an integer, an iterable of integers or a compact format string similar to those used in `pack` (described in Compact format strings). It defaults to 0, which means reverse as many bytes as possible. The fmt gives a pattern of byte sizes to use to swap the endianness of the `BitArray`. Note that if you use a compact format string then the endianness identifier (`<`, `>` or `=`) is not needed, and if present it will be ignored.

  start and end optionally give a slice to apply the transformation to (it defaults to the whole `BitArray`). If repeat is `True` then the byte swapping pattern given by the fmt is repeated in its entirety as many times as possible.

      >>> s = BitArray('0x00112233445566')
      >>> s.byteswap(2)
      3
      >>> s
      BitArray('0x11003322554466')
      >>> s.byteswap('h')
      3
      >>> s
      BitArray('0x00112233445566')
      >>> s.byteswap([2, 5])
      1
      >>> s
      BitArray('0x11006655443322')

  It can also be used to swap the endianness of the whole `BitArray`.

      >>> s = BitArray('uintle32=1234')
      >>> s.byteswap()
      >>> print(s.uintbe)
      1234

BitArray.clear() → None

  Removes all bits from the bitstring.

  `s.clear()` is equivalent to `del s[:]` and simply makes the bitstring empty.

BitArray.insert(bs: BitsType, pos: int) → None

  Inserts bs at pos.

  When used with the `BitStream` class the pos is optional, and if not present the current bit position will be used. After insertion the property `pos` will be immediately after the inserted bitstring.

      >>> s = BitStream('0xccee')
      >>> s.insert('0xd', 8)
      >>> s
      BitStream('0xccdee')
      >>> s.insert('0x00')
      >>> s
      BitStream('0xccd00ee')

BitArray.invert(pos: int | Iterable[int] | None = None) → None

  Inverts one or many bits from `1` to `0` or vice versa.

  pos can be either a single bit position or an iterable of bit positions. Negative numbers are treated in the same way as slice indices and it will raise `IndexError` if `pos < -len(s)` or `pos > len(s)`. The default is to invert the entire `BitArray`.

      >>> s = BitArray('0b111001')
      >>> s.invert(0)
      >>> s.bin
      '011001'
      >>> s.invert([-2, -1])
      >>> s.bin
      '011010'
      >>> s.invert()
      >>> s.bin
      '100101'

BitArray.overwrite(bs: BitsType, pos: int) → None

  Replaces the contents of the current `BitArray` with bs at pos.

  When used with the `BitStream` class the pos is optional, and if not present the current bit position will be used. After insertion the property `pos` will be immediately after the overwritten bitstring.

      >>> s = BitArray(length=10)
      >>> s.overwrite('0b111', 3)
      >>> s
      BitArray('0b0001110000')
      >>> s.pos
      6

BitArray.prepend(bs: BitsType) → None

  Inserts bs at the beginning of the current `BitArray`.

      >>> s = BitArray('0b0')
      >>> s.prepend('0xf')
      >>> s
      BitArray('0b11110')

BitArray.replace(old: BitsType, new: BitsType, start: int | None = None, end: int | None = None, count: int | None = None, bytealigned: bool | None = None) → int

  Finds occurrences of old and replaces them with new. Returns the number of replacements made.

  If bytealigned is `True` then replacements will only be made on byte boundaries. start and end give the search range and default to `0` and `len` respectively. If count is specified then no more than this many replacements will be made.

      >>> s = BitArray('0b0011001')
      >>> s.replace('0b1', '0xf')
      3
      >>> print(s.bin)
      0011111111001111
      >>> s.replace('0b1', '', count=6)
      6
      >>> print(s.bin)
      0011001111

BitArray.reverse(start: int | None = None, end: int | None = None) → None

  Reverses bits in the `BitArray` in-place.

  start and end give the range of bits to reverse and default to `0` and `len` respectively.

      >>> a = BitArray('0b000001101')
      >>> a.reverse()
      >>> a.bin
      '101100000'
      >>> a.reverse(0, 4)
      >>> a.bin
      '110100000'

BitArray.rol(bits: int, start: int | None = None, end: int | None = None) → None

  Rotates the contents of the `BitArray` in-place by bits bits to the left.

  start and end define the slice to use and default to `0` and `len` respectively.

  Raises `ValueError` if `bits < 0`.

      >>> s = BitArray('0b01000001')
      >>> s.rol(2)
      >>> s.bin
      '00000101'

BitArray.ror(bits: int, start: int | None = None, end: int | None = None) → None

  Rotates the contents of the `BitArray` in-place by bits bits to the right.

  start and end define the slice to use and default to `0` and `len` respectively.

  Raises `ValueError` if `bits < 0`.

BitArray.set(value: bool, pos: int | Iterable[int] | None = None) → None

  Sets one or many bits to either `1` (if value is `True`) or `0` (if value isn’t `True`). pos can be either a single bit position or an iterable of bit positions. Negative numbers are treated in the same way as slice indices and it will raise `IndexError` if `pos < -len(s)` or `pos > len(s)`. The default is to set every bit in the `BitArray`.

  Using `s.set(True, x)` can be more efficient than other equivalent methods such as `s[x] = 1`, `s[x] = "0b1"` or `s.overwrite('0b1', x)`, especially if many bits are being set. In particular using a `range` object as an iterable is treated as a special case and is done efficiently.

      >>> s = BitArray('0x0000')
      >>> s.set(True, -1)
      >>> print(s)
      0x0001
      >>> s.set(1, (0, 4, 5, 7, 9))
      >>> s.bin
      '1000110101000001'
      >>> s.set(0)
      >>> s.bin
      '0000000000000000'
      >>> s.set(1, range(0, len(s), 2))
      >>> s.bin
      '1010101010101010'

## Properties

Note that the `bin`, `oct`, `hex`, `int`, `uint` and `float` properties can all be shortened to their initial letter. Properties can also have a length in bits appended to them to make properties such as `u8` or `floatle64` (with the exception of the `bytes` property which uses a unit of bytes instead of bits, so `bytes4` is 32 bits long). These properties with lengths can be used to quickly create a new bitstring.

    >>> a = BitArray()
    >>> a.f32 = 17.6
    >>> a.h
    '418ccccd'
    >>> a.i7 = -1
    >>> a.b
    '1111111'

BitArray.bin: str

BitArray.b: str

  Writable version of `Bits.bin`.

BitArray.bfloat: float

BitArray.bfloatbe: float

BitArray.bfloatle: float

BitArray.bfloatne: float

  Writable versions of `Bits.bfloat` / `Bits.bfloatbe` / `Bits.bfloatle` / `Bits.bfloatne`.

BitArray.bool: bool

  Writable version of `Bits.bool`.

BitArray.bytes: bytes

  Writable version of `Bits.bytes`.

BitArray.hex: str

BitArray.h: str

  Writable version of `Bits.hex`.

BitArray.int: int

BitArray.i: int

  Writable version of `Bits.int`. The properties can have a bit length appended to it such as `i32` or `int5` to specify the new length of the bitstring. Using a length too small to contain the value given will raise a `CreationError`.

  When used as a setter without a new length the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

      >>> s = BitArray('0xf3')
      >>> s.int
      -13
      >>> s.int = 1232
      ValueError: int 1232 is too large for a BitArray of length 8.

BitArray.intbe: int

  Writable version of `Bits.intbe`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.intle: int

  Writable version of `Bits.intle`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.intne: int

  Writable version of `Bits.intne`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.float: float

BitArray.floatbe: float

BitArray.f: float

  Writable version of `Bits.float`. The standard `float`, the big-endian `floatbe` and the shortened `f` are all equivalent.

  The properties can have a bit length appended to them such as `f16` or `floatle64` to specify the new length of the bitstring. Using a length that doesn’t support any floating point types will raise a `CreationError`.

BitArray.floatle: float

  Writable version of `Bits.floatle`.

BitArray.floatne: float

  Writable version of `Bits.floatne`.

BitArray.e4m3float: float

  Writable version of `Bits.e4m3float`.

BitArray.e5m2float: float

  Writable version of `Bits.e5m2float`.

BitArray.oct: str

BitArray.o: str

  Writable version of `Bits.oct`.

BitArray.se: int

  Writable version of `Bits.se`.

BitArray.ue: int

  Writable version of `Bits.uie`.

BitArray.sie: int

  Writable version of `Bits.sie`.

BitArray.uie: int

  Writable version of `Bits.ue`.

BitArray.uint: int

BitArray.u: int

  Writable version of `Bits.uint`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.uintbe: int

  Writable version of `Bits.uintbe`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.uintle: int

  Writable version of `Bits.uintle`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

BitArray.uintne: int

  Writable version of `Bits.uintne`.

  When used as a setter the value must fit into the current length of the `BitArray`, else a `ValueError` will be raised.

## Special Methods

BitArray.__delitem__(key)

  `del s[start:end:step]`

  Deletes the slice specified.

BitArray.__iadd__(bs)

  `s1 += s2`

  Appends bs to the current bitstring.

  Note that for `BitArray` objects this will be an in-place change, whereas for `Bits` objects using `+=` will not call this method - instead a new object will be created (it is equivalent to a copy and an `__add__`).

      >>> s = BitArray(ue=423)
      >>> s += BitArray(ue=12)
      >>> s.read('ue')
      423
      >>> s.read('ue')
      12

BitArray.__iand__(bs)

  `s &= bs`

  In-place bit-wise AND between two bitstrings. If the two bitstrings are not the same length then a `ValueError` is raised.

BitArray.__ilshift__(n)

  `s <<= n`

  Shifts the bits in-place n bits to the left. The n right-most bits will become zeros and bits shifted off the left will be lost.

BitArray.__imul__(n)

  `s *= n`

  In-place concatenation of n copies of the current bitstring.

      >>> s = BitArray('0xbad')
      >>> s *= 3
      >>> s.hex
      'badbadbad'

BitArray.__ior__(bs)

  `s |= bs`

  In-place bit-wise OR between two bitstrings. If the two bitstrings are not the same length then a `ValueError` is raised.

BitArray.__irshift__(n)

  `s >>= n`

  Shifts the bits in-place n bits to the right. The n left-most bits will become zeros and bits shifted off the right will be lost.

BitArray.__ixor__(bs)

  `s ^= bs`

  In-place bit-wise XOR between two bitstrings. If the two bitstrings are not the same length then a `ValueError` is raised.

BitArray.__setitem__(key, value)

  `s1[start:end:step] = s2`

  Replaces the slice specified with a new value.

      >>> s = BitArray('0x00000000')
      >>> s[::8] = '0xf'
      >>> print(s)
      0x80808080
      >>> s[-12:] = '0xf'
      >>> print(s)
      0x80808f