如何更改屈服值

How to change a yielded value

以下代码使用上下文管理器将变量存储和加载到文件中。 但是,必须设置上下文管理器 (loaded.value) 生成的内容的 value 属性 非常烦人。 我愿意

  1. 不必像 LoadedValue
  2. 那样定义新的 class
  3. 将上下文管理器 (loaded) 的生成值设置为保存的值。

如果能解决其中任何一个问题,我们将不胜感激。

import os
import pickle
from contextlib import contextmanager

class LoadedValue:
    def __init__(self, value):
        self.value = value

    def __str__(self):
        return "<LoadedValue: {}>".format(self.value)

@contextmanager
def load_manager(load_file="file.pkl"):
    with open(load_file, "rb") as f:
        loaded_object = LoadedValue(pickle.load(f))
    try:
        yield loaded_object
    finally:
        with open(load_file, "wb+") as f:
            pickle.dump(loaded_object.value, f)

if __name__ == "__main__":
    filename = "test.pkl"
    with open(filename, "wb+") as f:
        pickle.dump(7, f)

    with load_manager(filename) as loaded:
        print(loaded) # >>> <LoadedValue: 7>
        loaded.value = 5 # this is what I have to do
        # loaded = 5  # this is what I want to do

    with load_manager(filename) as loaded:
        print(loaded) # >>> <LoadedValue: 5>

注意:这是 originally posted 在 CodeReview 上发表的,但我决定在此处重新发布它以获得答案,并将其留在 CodeReview 上以帮助以其他方式改进代码。

没有办法覆盖 python 中的赋值运算符,所以你不能做 loaded = 5

(你可以覆盖其他东西,这样它可能会起作用)

  • 覆盖 __call__ 以允许 loaded(5)
  • 覆盖 __lshift__ 以允许 loaded << 5
  • 覆盖 __ior__ 以允许 loaded |= 5

(但是要提前警告你的同事,否则未来的同事可能永远不会原谅你)

此外,在 with XXXX as Y: 块范围内发生的事情(通常)不能被产生上下文的方法访问,除非该范围先前可被产生范围的地方访问(即全局命名空间等)