如何在Python中迭代每个字节的每个位?

huangapple go评论112阅读模式
英文:

How to iterate over each bit of a byte in Python?

问题

让我们假设 a=0xF0b=[a的位列表]。我如何迭代遍历a的每个位,以便我可以执行位运算,将该位与列表b中的位进行位运算?

我已尝试使用bin()方法将a转换为其二进制形式,然后循环遍历它,但由于a的每个位现在都是字符串数据类型,因此无法再执行位运算。

任何帮助都将不胜感激!

英文:

Let's say a=0xF0 and b=[a list of bits]. How do I iterate over each bit of a so that i can perform a bitwise operation between that bit and a bit in list b?

I have tried converting a to its binary form using the bin() method before looping through it, however, i can no longer perform a bitwise operation as each bit of a is now of the string datatype.

Any help is appreciated!

答案1

得分: 0

你可以使用位移操作:

  1. a = 0xF0
  2. b = [1, 0, 1, 0, 1, 0, 1, 0]
  3. print(bin(a))
  4. # 0b11110000
  5. for idx, bit_in_b in enumerate(b):
  6. bit_in_a = (a >> idx) & 1
  7. binary_and_operation = bit_in_a & bit_in_b
  8. print(bit_in_a, binary_and_operation)
  9. # 0 0
  10. # 0 0
  11. # 0 0
  12. # 0 0
  13. # 1 1
  14. # 1 0
  15. # 1 1
  16. # 1 0

注意两点:

  • a 从右到左迭代,b 从左到右迭代,但根据需要可以更改。
  • 如果 len(b) 不等于 a 中的比特数,行为可能不是你想要的。
英文:

You can use bitshift:

  1. a = 0xF0
  2. b = [1, 0, 1, 0, 1, 0, 1, 0]
  3. print(bin(a))
  4. # 0b11110000
  5. for idx, bit_in_b in enumerate(b):
  6. bit_in_a = (a >> idx) & 1
  7. binary_and_operation = bit_in_a & bit_in_b
  8. print(bit_in_a, binary_and_operation)
  9. # 0 0
  10. # 0 0
  11. # 0 0
  12. # 0 0
  13. # 1 1
  14. # 1 0
  15. # 1 1
  16. # 1 0

Careful to 2 points:

  • a will be iterated from right to left and b from left to right, but you can change that as needed.
  • if len(b) != number of bits in a, behavior might not be what you want.

答案2

得分: 0

  1. 一种简短的表达方式如下
  2. ```python
  3. bin(int("".join([str(bit) for bit in b]), 2) ^ a)[2:].zfill(max(len(b), (len(bin(a)) - 2)))

它的工作原理如下:

  • "".join([str(bit) for bit in b]) 将您的列表转换为字符串
  • int(..., 2) 转换为二进制数字
  • ^ 是按位异或运算(或者任何其他您想要的操作)
  • bin(...) 将其转换回二进制表示
  • [2:] 去除字符串的 0b 部分
  • .zfil(...) 填充结果的零,直到结果具有与两个输入中较大者相同数量的位数,以防位运算结果以零开头。

示例:

  1. a = 0xF0
  2. b = [0, 1, 1, 1, 0, 0, 1, 0]
  3. result = bin(int("".join([str(bit) for bit in b]), 2) ^ a)[2:].zfill(max(len(b), (len(bin(a)) - 2)))
  4. print(result)

输出:

  1. 10000010
  1. <details>
  2. <summary>英文:</summary>
  3. A one-liner would be this:

bin(int("".join([str(bit) for bit in b]), 2) ^ a)[2:].zfill(max(len(b), (len(bin(a))-2)))

  1. It works like so:
  2. - `&quot;&quot;.join([str(bit) for bit in b]` converts your list to a string
  3. - `int(..., 2)` converts to a number in base 2
  4. - `^` is the bitwise `xor` (or any other operation you want)
  5. - `bin(...)` converts it back to a binary representation
  6. - `[2:]` drops the `0b` part of the string
  7. - `.zfil(...)` pads the result with zeroes until the result has the same number of bits as the largest of the two inputs, in case the bitwise result starts with zeroes.
  8. Example:

a = 0xF0
b = [0, 1, 1, 1, 0, 0, 1, 0]
result = bin(int("".join([str(bit) for bit in b]), 2) ^ a)[2:].zfill(max(len(b), (len(bin(a))-2)))
print(result)

  1. Output:

10000010

  1. </details>

huangapple
  • 本文由 发表于 2023年7月13日 16:33:26
  • 转载请务必保留本文链接:https://go.coder-hub.com/76677402.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定