Python đánh giá chính xác các thuộc tính lớp như thế nào? Tôi đã tình cờ gặp một điều thú vị (trong Python 2.5.2) mà tôi muốn giải thích.Đánh giá và tạo thuộc tính lớp
Tôi có một lớp học với một số thuộc tính được xác định theo các thuộc tính khác, được xác định trước đó. Khi tôi cố gắng sử dụng một đối tượng máy phát điện, Python ném một lỗi, nhưng nếu tôi sử dụng một danh sách đồng bằng thông thường, thì không có vấn đề gì.
Đây là ví dụ minh họa. Lưu ý rằng sự khác biệt duy nhất là Brie
sử dụng biểu thức trình tạo, trong khi Cheddar
sử dụng tính năng hiểu danh sách.
# Using a generator expression as the argument to list() fails
>>> class Brie :
... base = 2
... powers = list(base**i for i in xrange(5))
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 3, in Brie
File "<stdin>", line 3, in <genexpr>
NameError: global name 'base' is not defined
# Using a list comprehension works
>>> class Cheddar :
... base = 2
... powers = [base**i for i in xrange(5)]
...
>>> Cheddar.powers
[1, 2, 4, 8, 16]
# Using a list comprehension as the argument to list() works
>>> class Edam :
... base = 2
... powers = list([base**i for i in xrange(5)])
...
>>> Edam.powers
[1, 2, 4, 8, 16]
(trường hợp thực tế của tôi là phức tạp hơn, và tôi đã tạo ra một dict, nhưng đây là ví dụ tối thiểu tôi có thể tìm thấy.)
đoán duy nhất của tôi là rằng comprehensions danh sách được tính tại dòng đó , nhưng các biểu thức máy phát điện được tính sau khi kết thúc lớp, tại thời điểm đó phạm vi đã thay đổi. Nhưng tôi không chắc tại sao biểu thức máy phát không hoạt động như một đóng và lưu trữ tham chiếu đến cơ sở trong phạm vi tại dòng.
Có lý do nào cho điều này không, và nếu có, tôi nên suy nghĩ như thế nào về cơ chế đánh giá thuộc tính lớp?