Базовый механизм для поиска членов класса Python - PullRequest
2 голосов
/ 12 октября 2011

В Python, если я определю три класса:

class A:
    name = 'oliver'
    hailstone_ending = [4,2,1]

class B:
    def __init__(self):
        self.name = 'oliver'
        self.hailstone_ending = [4,2,1]

class C:
    pass

c = C()
c.name = 'oliver'
c.hailstone_ending = [4,2,1]

Под капотом функционирует ли поиск членов одинаково для каждого класса? Кажется, что A понадобится только в словаре для поиска членов для всех экземпляров; C, с другой стороны, потребуется использовать словарь, хранящийся в каждом из этих экземпляров. Если бы переводчик был очень умен, теоретически он мог бы заметить, что все экземпляры B должны включать членов name и hailstone_ending; следовательно, это может быть эквивалентно A.

Но, с другой стороны, если операция del разрешена в словаре, который ищет членов класса, механизм поиска во всех этих классах может быть эквивалентен, поскольку доступные члены будут зависеть от экземпляра.

Меня интересует, что у меня был какой-то код, который создал несколько тысяч классов типа C, и я заметил, что он очень медленный и требует много памяти. Недавно я переписал его по-другому, и он кажется мне более эффективным (но я не проверял его строго, и поэтому он может быть таким же).

Большое спасибо за понимание!

Ответы [ 2 ]

2 голосов
/ 12 октября 2011

Под капотом функционирует ли поиск членов одинаково для каждого класса?

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

Кажется, что A понадобится только в словаре для поиска членов во всех случаях; C, с другой стороны, потребуется использовать словарь, хранящийся в каждом из этих экземпляров. Если бы интерпретатор был очень умным, он теоретически мог бы заметить, что все экземпляры B должны включать имена членов и hailstone_ending; следовательно, это может быть эквивалентно A.

В A атрибуты хранятся в A.__dict__, то есть в типе. В B и C атрибуты хранятся в self.__dict__, то есть в экземпляре. Оба словаря присутствуют во всех случаях. Там больше ничего нет. И нет, между B и C.

нет никакой разницы
2 голосов
/ 12 октября 2011

В python каждый класс и каждый экземпляр получает словарь. A использует словарь классов. В примерах для классов B и C используются словари экземпляров. B не будет эквивалентен A - python не предназначен быть быстрым, было бы очень трудно, если не невозможно доказать, что никакие экземпляры B не будут мутированы.

Доказательство:

* * 1010

Ваш вопрос заставляет меня задуматься о прототипах javascript.

Также: поиск членов может возвращаться к словарю классов, если член не найден в словаре экземпляров, но при записи будет использоваться словарь экземпляров.

...