【问题标题】:Which method is most Pythonic? Handling if a variable exists哪种方法最 Pythonic?处理变量是否存在
【发布时间】:2017-08-05 01:41:24
【问题描述】:

我有多个使用单个变量的函数,这个变量的计算成本很高,所以我不想重复这个。我有两种简单的建议方法来做到这一点,并且想知道您觉得哪个更“pythonic”或更好的方法。

class A:

    def __init__(self):
        self.hasAttr = False

    def compute_attr(self):
        self.attr = 10
        self.hasAttr = True #for func2 only

    def func1(self):
        try:
            print self.attr == 10
        except AttributeError:
            self.compute_attr()
            self.func1()

    def func2(self):
        if not self.hasAttr: self.compute_attr()
        print self.attr == 10

a = A()
a.func1()
a.func2()

func1 使用一个简单的尝试,除了在这种情况下捕获 AttributeError 并计算属性。 func2 使用存储的布尔值来检查计算是否已完成。

是否有任何理由认为一种方法优于另一种方法?此外,在 func2 中定义一个进行检查的装饰器是否有任何意义?

感谢您的帮助。

【问题讨论】:

标签: python methods python-decorators


【解决方案1】:

基本上你的问题是“should I use EAFP or should I use LBYL”。答案是:视情况而定。 try/except 块几乎可以免费设置,但在使用时(当实际引发异常时)非常昂贵,而测试的成本是恒定的(对于这种测试来说相当便宜),所以如果你经常没有您可能更喜欢 LBYL 解决方案的属性集,而如果您确信它在大多数情况下已经设置,那么 EAFP 可能是更好的选择。

请注意,还有更简单(且更可靠)的方法来测试您的属性是否已被计算 - 或者通过在初始化程序中使用标记值设置它 - None 是一个明显的候选者,除非它也恰好是有效的值 - 或使用hasattr(obj, attrname)。也可以使用属性来封装访问,即:

class EAFB(object):

    @property
    def attr(self):
        try:
            return self._attr
        except AttributeError:
            self._attr = costly_computation()
            return self._attr


   def func(self):
       print "attr is %s" % self.attr



class LBYL(object):

    @property
    def attr(self):
        if not hasattr(self, "_attr"):
            self._attr = costly_computation()
        return self._attr


   def func(self):
       print "attr is %s" % self.attr

【讨论】:

  • 在 python 中还没有遇到 property 函数,也没有遇到 EAFP 或 LBYL 范例。使用属性作为装饰器是我将采用的方式(使用 EAFP 方法,通常应该已经初始化了事物)。感谢您回答使用哪种方法的问题。我现在看到这个问题可能是重复的,但是这个答案比我在其他类似问题中看到的答案要清楚得多。谢谢
猜你喜欢
  • 2012-02-15
  • 1970-01-01
  • 1970-01-01
  • 2018-09-30
  • 2010-11-14
  • 1970-01-01
  • 2013-04-25
  • 1970-01-01
  • 2015-10-19
相关资源
最近更新 更多