python - 一个实例属性引用另一个实例属性,并在类实例化后进行更新

标签 python class instance-variables

我正在寻找有关设置一个实例属性的最佳实践,该实例属性在类实例化后引用另一个实例属性。

例如:

class Foo:
    def __init__(self):
        self.a = 1
        self.b = self.a + 1
>>> obj_foo = Foo()
>>> obj_foo.a
1
>>> obj_foo.b
2
>>> obj_foo.a = 5
>>> obj_foo.a
5
>>> obj_foo.b
2 # I want this to be 6

一个实例属性引用另一个实例属性是不好的做法吗?

我可以看到如何实现一种方法来检查和更新依赖实例属性,但这似乎有很多开销/hacky。非常感谢任何帮助!

最佳答案

看起来您实际上根本不想存储 b 的值,而是想根据 a 的值动态生成它。幸运的是,有一个property您可以仅用于此目的的类/装饰器:

class Foo:
    def __init__(self, a=1):
        self.a = a

    @property
    def b(self):
        return self.a + 1

这将创建一个只读属性 b,当您作为 foo.b 访问它时,它的行为就像普通属性一样,但会是 a,因为它是 a descriptor 。它将根据 foo.a 设置的内容重新计算值。

您对每次调用方法进行计算的担心并非完全没有道理。使用 . 运算符已经执行了一些相当昂贵的查找,因此您的玩具箱没有问题,如上所示。但您经常会遇到需要的不仅仅是在参数中加 1 的情况。在这种情况下,您将需要使用缓存之类的东西来加快速度。例如,您可以将 a 设为可设置的属性。每当 a 的值更新时,您都可以以某种方式“无效”b,例如设置标志,或者只是将 None 分配给缓存的值。现在,您昂贵的计算仅在必要时运行:

class Foo:
    def __init__(self, a=1):
        self._a = a

    @property
    def a(self):
        return self._a

    @a.setter
    def a(self, value):
        self._a = value
        self._b = None

    @property
    def b(self):
        if self._b is None:
            # Placeholder for expensive computation here
            self._b = self._a + 1
        return self._b

在此示例中,在 __init__ 中设置 self.a = a 将触发属性 foo.a 的 setter,确保属性 foo._b 始终存在。

关于python - 一个实例属性引用另一个实例属性,并在类实例化后进行更新,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59569939/

相关文章:

java - 在 junit 测试中获取一个类作为 javax.lang.model.element.Element

C# 构造函数 - 设置第二个属性

ruby - 在 Ruby 中继承类级实例变量?

C++ 实例变量/指向堆中数组的指针

python - 理解非齐次 numpy 数组

python - Pandas:如何根据表示两列中的值的元组列表从数据框中删除行?

检查软件包是否安装的 Pythonic 方法

Python 2.7 运行时代码更改

用于管理对数据库的访问的 C++ 类

javascript - Javascript 类中的实例变量