mmap — Поддержка отображаемых в память файлов


Отображаемые в память файловые объекты ведут себя как bytearray и подобные файловым объектам. Объекты mmap можно использовать в большинстве мест, где ожидаются bytearray; например, модуль re можно использовать для поиска по файлу, сопоставленному с памятью. Можно также изменить один байт, выполнив команду obj[index] = 97, или изменить подпоследовательность, назначив слайсу: obj[i1:i2] = b'...'. Вы можете также прочитать и написать данные, начинающиеся в текущей позиции файла и seek() через файл к различным позициям.

Сопоставленный с памятью файл создается конструктором mmap, который отличается в Unix и Windows. В любом случае необходимо предоставить файл дескриптор для файла, открытого для обновления. Если вы хотите нанести на карту существующий объект файла Python, используйте его метод fileno(), чтобы получить правильный значение для параметра fileno. Иначе вы можете открыть файл, используя функцию os.open(), который возвращает файловый дескриптор непосредственно (файл все еще должен быть закрыт, когда он сделан).

Примечание

Если вы хотите создать отображение памяти для перезаписываемого, буферизированного файла, вы должны сначала выполнить flush() файл. Это необходимо, чтобы гарантировать, что модификации локальная к буферам на самом деле доступны отображению.

Как для Unix, так и для Windows-версий конструктора, access может быть указан как необязательный параметр ключевой. access принимает одно из четырех значения: ACCESS_READ, ACCESS_WRITE или ACCESS_COPY для указания памяти, доступной только для чтения, сквозной записи или копирования при записи, соответственно, или ACCESS_DEFAULT для переноса на prot. access может быть используемый и на Unix и на Windows. Если параметр access не указан, Windows mmap возвращает сопоставление сквозной записи. Начальная память значения для всех трех типов доступа взята из указанного файла. Назначение на карту памяти ACCESS_READ вызывает исключение TypeError. Назначение на карту памяти ACCESS_WRITE влияет как на память, так и на базовый файл. Назначение на карту памяти ACCESS_COPY влияет на память, но не обновляет базовый файл.

Изменено в версии 3.7: Добавленная константа ACCESS_DEFAULT.

Для отображения анонимной памяти в качестве fileno следует передать значение -1 вместе с длиной.

class mmap.mmap(fileno, length, tagname=None, access=ACCESS_DEFAULT[, offset])

(Windows версия) Отображает length байт из файла определенного файлого обработчика fileno и создает объект mmap. Если length больше, чем текущий размер файла, файл расширен, чтобы содержать байты length. Если length равно 0, максимальная длина карты - текущий размер файла, за исключением того, что если файл пуст, возникает исключение (невозможно создать пустое сопоставление в Windows).

tagname, если указано, а не None, является строка, дающим имя тега для сопоставления. Windows позволяет использовать множество различных сопоставлений с одним и тем же файлом. Если указано имя существующего тега, этот тег открывается, в противном случае создается новый тег с таким именем. Если этот параметр опущен или None, сопоставление создается без имени. Отказ от использования параметра тега поможет сохранить ваш код переносимым между Unix и Windows.

offset может быть указан как неотрицательное целое смещение. ссылки mmap будут относиться к смещению от начала файла. offset по умолчанию имеет значение 0. offset должно быть кратным ALLOCATIONGRANULARITY.

Поднимает событие аудита mmap.__new__ с аргументами fileno, length, access, offset.

class mmap.mmap(fileno, length, flags=MAP_SHARED, prot=PROT_WRITE|PROT_READ, access=ACCESS_DEFAULT[, offset])

(Unix версия) Отображает length байт из файла определенного файловым дескриптором fileno и возвращая объект mmap. Если length равно 0, максимальная длина карты будет равна текущему размеру файла при вызове mmap.

flags определяет характер сопоставления. MAP_PRIVATE создает частное сопоставление копирования при записи, поэтому изменения в содержимом объекта mmap будут закрытыми для этого процесса, а MAP_SHARED создает сопоставление, совместно используемое со всеми другими процессами, отображающими те же области файла. Дефолт значение является MAP_SHARED.

prot, если указано, обеспечивает требуемую защиту памяти; двумя наиболее полезными значения являются PROT_READ и PROT_WRITE, чтобы указать, что страницы могут быть прочитаны или написаны. prot по умолчанию принимает значение PROT_READ | PROT_WRITE.

access может быть указан вместо flags и prot в качестве необязательного параметра ключевой. Ошибка при указании flags, prot и access. Для получения информации об использовании этого параметра см. описание access выше.

offset может быть указан как неотрицательное целое смещение. ссылки mmap будут относиться к смещению от начала файла. offset по умолчанию имеет значение 0. offset должно быть кратным ALLOCATIONGRANULARITY, что равно PAGESIZE в системах Unix.

Для обеспечения достоверности отображения созданной памяти файл, указанный в файле дескриптор fileno, автоматически синхронизируется с физическим хранилищем резервных данных в Mac OS X и OpenVMS.

В этом примере показан простой способ использования mmap:

import mmap

# записать простой пример файла
with open("hello.txt", "wb") as f:
    f.write(b"Hello Python!\n")

with open("hello.txt", "r+b") as f:
    # отображаемый в память файл, размер 0 означает весь файл
    mm = mmap.mmap(f.fileno(), 0)
    # читать содержимое с помощью стандартных файловых методов
    print(mm.readline())  # prints b"Hello Python!\n"
    # прочитать содержимое через слайс представление
    print(mm[:5])  # печать b"Hello"
    # обновить содержимое, используя нотацию слайса;
    # обратите внимание, что новый контент должен иметь одинаковый размер
    mm[6:] = b" world!\n"
    # ... и прочитать снова, используя стандартные методы файла
    mm.seek(0)
    print(mm.readline())  # печать b"Hello  world!\n"
    # закрыть отображение
    mm.close()

mmap может также быть используемый как менеджер контекста в with инструкции:

import mmap

with mmap.mmap(-1, 13) as mm:
    mm.write(b"Hello world!")

Добавлено в версии 3.2: Менеджер контекста поддержка.

В следующем примере показано, как создать анонимную карту и обмениваться данными между родительскими и дочерними процессами:

import mmap
import os

mm = mmap.mmap(-1, 13)
mm.write(b"Hello world!")

pid = os.fork()

if pid == 0:  # В дочернем процессе
    mm.seek(0)
    print(mm.readline())

    mm.close()

Поднимает событие аудита mmap.__new__ с аргументами fileno, length, access, offset.

Объекты файла, сопоставленные с памятью, поддерживают следующие методы:

close()

Закрытие mmap. Последующие вызовы других методов объекта приведут к возникновению исключения CreateError. Открытый файл не будет закрыт.

closed

True, если файл закрыт.

Добавлено в версии 3.2.

find(sub[, start[, end]])

Возвращает наименьший индекс в объекте, где обнаружена подпоследовательность sub, такой, что sub содержится в диапазоне [start, end]. Необязательные аргументы start и end интерпретируются как в слайсе. Возвращает -1 при сбое.

Изменено в версии 3.5: Теперь допускается запись в байтоподобный объект.

flush([offset[, size]])

Очистка изменений, внесенных в копию файла, находящуюся в памяти, обратно на диск. Без использования этого вызова нет гарантии, что изменения будут записаны до уничтожения объекта. Если указаны offset и size, на диск будут сброшены только изменения заданного диапазона байтов; в противном случае весь объем отображения очищается. offset должно быть кратным PAGESIZE или ALLOCATIONGRANULARITY.

None возвращенный указывает на успех. При сбое вызова возникает исключение.

Изменено в версии 3.8: Ранее, отличный от нуля значение был возвращенный на успехе; нуль был возвращенный при ошибке в Windows. Ноль значение был возвращенный на успехе; возникло исключение при ошибке в Unix.

madvise(option[, start[, length]])

Отправьте в ядро совет option о том, что область памяти начинается с start и расширяет length байт. option должен быть одним из доступных MADV_* константы на системе. Если параметры start и length опущены, все отображение выполняется по всему спектру. В некоторых системах (включая Linux) start должен быть кратен PAGESIZE.

Доступность: системы с системным вызовом madvise().

Добавлено в версии 3.8.

move(dest, src, count)

Скопировать count байт, начинающиеся со смещения src, в целевой индекс dest. Если mmap была создана с помощью ACCESS_READ, то вызовы для перемещения вызовут исключение TypeError.

read([n])

Возвращает bytes, содержащий до n байт, начиная с текущей позиции файла. Если аргумент опущен, None или отрицательный, возвращает все байты из текущей позиции файла в конец сопоставления. Позиция файла обновляется для указания после возвращенный байтов.

Изменено в версии 3.3: Аргумент может быть опущен или None.

read_byte()

Возвращает байт в текущей позиции файла в виде целого числа и продвигает позицию файла на 1.

readline()

Возвращает одну строку, начиная с текущей позиции файла и вплоть до следующей новой строки.

resize(newsize)

Изменение размеров карты и базового файла, если таковой имеется. Если mmap была создана с помощью ACCESS_READ или ACCESS_COPY, изменение размера карты вызовет исключение TypeError.

rfind(sub[, start[, end]])

Возвращает наивысший индекс в объекте, где находится подпоследовательность sub, такой, что sub содержится в диапазоне [start, end]. Необязательные аргументы start и end интерпретируются как в срезе. Возвращает -1 о сбое.

Изменено в версии 3.5: Теперь допускается запись в байтоподобный объект.

seek(pos[, whence])

Задать текущее положение файла. Аргумент whence необязателен и по умолчанию имеет значение os.SEEK_SET или 0 (абсолютное позиционирование файлов); другими значения являются os.SEEK_CUR или 1 (поиск относительно текущей позиции) и os.SEEK_END или 2 (поиск относительно конца файла).

size()

Возвращает длину файла, которая может быть больше размера области отображения памяти.

tell()

Возвращает текущее положение указателя файла.

write(bytes)

Запишите байты в bytes в память в текущем положении указателя файла и возвращает количество записанных байтов (никогда не меньше len(bytes), так как при сбое записи будет поднят ValueError). Позиция файла обновляется для указания после записанных байтов. Если mmap была создана с помощью ACCESS_READ, то запись в нее вызовет исключение TypeError.

Изменено в версии 3.5: Теперь допускается запись в байтоподобный объект.

Изменено в версии 3.6: Число записанных байт теперь равно возвращенный.

write_byte(byte)

Запишите целое число byte в память в текущем положении указателя файла; положение файла увеличивается на 1. Если mmap была создана с помощью ACCESS_READ, то запись в нее вызовет исключение TypeError.

MADV_* константы

mmap.MADV_NORMAL
mmap.MADV_RANDOM
mmap.MADV_SEQUENTIAL
mmap.MADV_WILLNEED
mmap.MADV_DONTNEED
mmap.MADV_REMOVE
mmap.MADV_DONTFORK
mmap.MADV_DOFORK
mmap.MADV_HWPOISON
mmap.MADV_MERGEABLE
mmap.MADV_UNMERGEABLE
mmap.MADV_SOFT_OFFLINE
mmap.MADV_HUGEPAGE
mmap.MADV_NOHUGEPAGE
mmap.MADV_DONTDUMP
mmap.MADV_DODUMP
mmap.MADV_FREE
mmap.MADV_NOSYNC
mmap.MADV_AUTOSYNC
mmap.MADV_NOCORE
mmap.MADV_CORE
mmap.MADV_PROTECT

Эти параметры можно передать mmap.madvise(). Не каждый вариант будет присутствовать в каждой системе.

Доступность: системы с системным вызовом madvise().

Добавлено в версии 3.8.