Что делает Python sys.intern и когда его следует использовать? - PullRequest
43 голосов
/ 16 июля 2009

Я сталкивался с этим вопросом об управлении памятью словарей, в котором упоминается функция intern . Что именно он делает и когда будет использоваться?

Чтобы привести пример:

Если у меня есть набор с именем visible , который содержит кортежи в форме (string1, string2), которые я использую для проверки на наличие дубликатов, будет храниться (intern (string1), intern (string2)) улучшить производительность по сравнению с память или скорость?

Ответы [ 5 ]

60 голосов
/ 16 июля 2009

Из документации Python 3 :

sys.intern(string)

Ввести строку в таблицу «интернированных» строк и вернуть интернированная строка - которая является самой строкой или копией. Интернаты полезно немного повысить производительность при поиске в словаре - если ключи в словаре интернированы, а ключ поиска интернирован, сравнение ключей (после хеширования) может быть выполнено с помощью сравнения указателей вместо сравнения строк. Обычно имена, используемые в Python программы автоматически интернируются, а словари используются для хранения Атрибуты модуля, класса или экземпляра имеют внутренние ключи.

Стажированные строки не бессмертны; Вы должны сохранить ссылку на верните значение intern (), чтобы получить выгоду от него.

Разъяснение

Как следует из документации, функция sys.intern предназначена для оптимизации производительности .

Функция sys.intern поддерживает таблицу из интернированных строк. Когда вы пытаетесь интернировать строку, функция ищет ее в таблице и:

  1. Если строка не существует (еще не была интернирована), функция сохраняет это в таблице и возвращает это из таблицы интернированных строк.

    >>> import sys
    >>> a = sys.intern('why do pangolins dream of quiche')
    >>> a
    'why do pangolins dream of quiche'
    

    В приведенном выше примере a содержит интернированную строку. Даже при том, что это невидимо, функция sys.intern сохранила строковый объект 'why do pangolins dream of quiche' в таблице интернированных строк.

  2. Если строка существует (была интернирована), функция возвращает ее из таблица интернированных строк.

    >>> b = sys.intern('why do pangolins dream of quiche')
    >>> b
    'why do pangolins dream of quiche'
    

    Даже если это не сразу видно, потому что строка 'why do pangolins dream of quiche' была интернирована раньше, b теперь содержит тот же строковый объект, что и a.

    >>> b is a
    True
    

    Если мы создадим одну и ту же строку без использования intern, мы получим два разных строковых объекта с одинаковым значением.

    >>> c = 'why do pangolins dream of quiche'
    >>> c is a
    False
    >>> c is b
    False
    

Используя sys.intern, вы гарантируете, что никогда не создадите два строковых объекта с одинаковым значением - когда вы запрашиваете создание второго строкового объекта с тем же значением, что и у существующего строкового объекта, вы получаете ссылку на предварительно Существующий строковый объект. Таким образом, вы экономите память . Кроме того, сравнение строковых объектов теперь очень эффективно , поскольку оно выполняется путем сравнения адресов памяти двух строковых объектов вместо их содержимого.

17 голосов
/ 16 июля 2009

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

Тем не менее, Python автоматически будет вводить строки небольшого размера или выглядеть как идентификаторы , поэтому вы можете обнаружить, что вы не добились улучшения, потому что ваши строки уже интернированы. Например:

>>> a = 'abc'; b = 'abc'
>>> a is b
True

В прошлом одним недостатком было то, что интернированные строки были постоянными. После интернирования строковая память никогда не освобождалась даже после удаления всех ссылок. Я думаю, что это больше не относится к более поздним версиям Python.

11 голосов
/ 16 июля 2009

Они не говорили о ключевом слове intern, потому что в Python такого нет. Они говорили о несущественной встроенной функции intern. Который в py3k был перемещен в sys.intern. Документы имеют исчерпывающее описание.

4 голосов
/ 16 июля 2009

Возвращает канонический экземпляр строки.

Поэтому, если у вас много одинаковых строковых экземпляров, вы экономите память, и кроме того, вы также можете сравнивать канонизированные строки по тождеству, а не по равенству, что быстрее.

0 голосов
/ 07 августа 2013

Эта идея появляется вокруг нас на нескольких языках, включая Python, Java и т. Д.

String Interning

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