Подтвердить что ты не робот

Зачем нам здесь быть здесь?

Я читаю исходный код, который загружает zip файл и считывает данные в массив numpy. Код должен работать на macos и linux, и вот фрагмент, который я вижу:

def _read32(bytestream):
    dt = numpy.dtype(numpy.uint32).newbyteorder('>')
    return numpy.frombuffer(bytestream.read(4), dtype=dt)

Эта функция используется в следующем контексте:

with gzip.open(filename) as bytestream:
    magic = _read32(bytestream)

Нетрудно видеть, что здесь происходит, но я озадачен целью newbyteorder('>'). Я прочитал документацию и знаю, что означают понятия endianness, но не может понять, почему именно разработчик добавил newbyteorder (по-моему, это действительно не нужно).

4b9b3361

Ответ 1

Это потому, что загруженные данные находятся в формате большого конца, как описано в исходной странице: http://yann.lecun.com/exdb/mnist/

Все целые числа в файлах сначала хранятся в MSB (высокий endian), используемый большинством процессоров, отличных от Intel. Пользователи Intel процессоры и другие низкоуровневые машины должны перевернуть байты заголовок.

Ответ 2

Это всего лишь способ убедиться, что байты интерпретируются из результирующего массива в правильном порядке независимо от системного байта.

По умолчанию встроенные NumPy-типы dtypes будут использовать байтовый блок, который является родным для вашей системы. Например, моя система малозначна, поэтому простое использование dtype numpy.dtype(numpy.uint32) будет означать, что значения, считанные в массиве из буфера с байтами в порядке big-endian, не будут интерпретироваться правильно.

Если np.frombuffer предназначено для получения байтов, которые, как известно, находятся в определенном байте, лучше всего использовать dtype, используя newbyteorder. Это указано в документах для np.frombuffer:

Примечания

Если в буфере есть данные, которые не находятся в байтовом порядке машины, это должно быть указано как часть типа данных, например:

>>> dt = np.dtype(int)
>>> dt = dt.newbyteorder('>')
>>> np.frombuffer(buf, dtype=dt)

Данные результирующего массива не будут байтами, но будут правильно интерпретируется.