Why Can’t I Compare a Two-Byte Slice Directly With a Hex Value?
Asked by
MellowQuill47
I'm writing a Python library to quickly parse RAW files from a Sony camera. To detect the file's byte order, I originally used this code:nn```pythonndef check_for_endian(data: bytes) -> tuple[int, int] | None:n if data[:2] == 0x4949: # "II" little-endiann return 1, 0n if data[:2] == 0x4D4D: # "MM" big-endiann return 2, 0n return Nonen```nnThat no longer appears to work in Python 3.13.9, so I changed it to unpack the first bytes with `struct`. Did comparing a bytes slice with a hexadecimal integer ever work, or was the original comparison invalid from the beginning?
Answers
If you keep using `struct`, make sure you unpack only the bytes you need. For example, `struct.unpack_from("<H", data, 0)[0]` reads an unsigned two-byte value. Using `unpack_from` without limiting the format is not necessary here. Also, comparing with `b"II"` or `b"MM"` avoids questions about integer byte order entirely.
Reply to this answer
A `bytes` slice and an integer are different types. In Python 3, `data[:2] == 0x4949` evaluates to `False`; it isn’t a valid way to compare the two-byte sequence with an integer. The simplest solution is to compare against a bytes literal:nn```pythonndef check_for_endian(data: bytes) -> tuple[int, int] | None:n if data[:2] == b"II":n return 1, 0n if data[:2] == b"MM":n return 2, 0n return Nonen```nnYou can also use `b"\x49\x49"` and `b"\x4d\x4d"` if you prefer hexadecimal notation. Your `struct` approach can work too, but unpacking is unnecessary when you only need to inspect the raw header bytes.
Reply to this answer
Add your answer
Answers are reviewed before publication.
MellowQuill47: Thanks! I’ll switch to comparing against byte literals. I’m certain the old version seemed to work before, but I can’t reproduce that behavior now; the only recent system change was an operating-system upgrade.