【问题标题】:How can I preserve or identify a caller's stack frame?如何保存或识别调用者的堆栈帧?
【发布时间】:2011-01-16 15:09:16
【问题描述】:

今天我的大脑感觉很慢。

我正在使用装饰器在 Python 中编写前/后/不变量。目前,我需要每次调用都为上下文指定局部变量和全局变量,这感觉很难看。有没有办法从装饰器应用程序级别获取局部变量和全局变量,即使它是任意深度。

也就是说,我正在尝试制作这个丑陋的代码: from dectools import invariant, pre, post, call_if

@invariant("self.price >= 0 and self.inventory >= 0 and Item.tax_rate >= 0")
class Item(object):
    tax_rate = 0.10  # California.  No property taxes on old property.

    @post("ItemDB.fetch(self) = (name, price)", locals(), globals())
    def __init__(self, name, price):
        self.name = name
        self.price = price
        self.total_sold = 0
        self.inventory = 0

    @call_if(check_level, "manager")
    @post("self.total_sold > 0", locals(), globals())
    @pre("discount > 0 and discount <= self.price * 0.50", locals(), globals())
    def adjust_price(self, adjustment):
         ....

进入相同的丑陋代码,没有所有“locals(), globals()”。我遇到了嵌套装饰器给我任意堆栈深度的问题,因此我的 dectools.pre 实现无法从恒定深度 sys._getframe() 中获取。堆栈不是我玩过的东西,如果有人有技巧,我会很感激。 (是的,我通过假设 self 将在正确的堆栈框架中将局部变量破解为局部变量。它是 Item.tax_rate 始终超出范围,self 和 ItemDB。)

提前谢谢你,

查尔斯

【问题讨论】:

    标签: python stack decorator


    【解决方案1】:

    如果您可以访问self.total_sold,则可以访问self.tax_rate(这与Item.tax_rate 相同,除非您踩踏它——所以您只是不要踩踏它,保持税率为原始类变量,并通过self.!-) 访问它。这将更多比通过堆栈更可靠,尤其是图片中的嵌套装饰器,这或多或少保证了脆弱的、特定版本相关的代码(堆栈自省旨在用于调试目的,本质上,用于生产目的)。

    【讨论】:

      猜你喜欢
      • 2011-06-23
      • 2012-08-03
      • 1970-01-01
      • 2019-08-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多