通过设计,属性获取器是否应该在python中引发异常? [英] By design should a property getter ever throw an exception in python?

查看:79
本文介绍了通过设计,属性获取器是否应该在python中引发异常?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于问题的某些上下文-我正在使用延迟加载将类中某些属性的完全初始化推迟到需要它们的时刻(如果有的话),因为它们的计算量可能很大。

For some context to the question - I am using lazy loading to defer full initialization of certain properties in a class until the point at which they are needed (if at all) as they can be computationally expensive to calculate.

我的问题是-在python中,如果在计算属性的值时发生错误,或者无法计算该值,则引发可接受的异常,还是客观上不好

My question is - in python if when calculating the value of the property an error occurs, or the value can't be calculated, is raising an exception acceptable or is it an objectively bad idea?

我知道这个问题:最佳做法:从属性中抛出异常-在遍历所有要点后实际上改写了这个问题。

I am aware of this question: Best practices: throwing exceptions from properties - and actually reworded this question after going over the points in it.

但是我真正想要的是关于python的明确答案。
例如,即使该值为无,getter还是应该始终返回该值?
在其他语言中,例如c#,对于如何设计属性有明确的建议。

However I am really looking for a definitive answer with regards to python. For example should a getter always return a value even if that value is None? In other languages, such as c#, there are clear recommendations on how to design properties.


避免从属性获取器抛出异常

AVOID throwing exceptions from property getters.

属性获取器应该是简单的操作,并且不应该有任何
前提条件。如果getter可以引发异常,则应该将
重新设计为一种方法。请注意,此规则不适用于
索引器,我们确实希望通过验证
参数而导致异常

Property getters should be simple operations and should not have any preconditions. If a getter can throw an exception, it should probably be redesigned to be a method. Notice that this rule does not apply to indexers, where we do expect exceptions as a result of validating the arguments

http://msdn.microsoft.com/en-us/library /ms229006.aspx

在python中是否也是如此?这个属性真的应该是一种方法吗?
我可以看到在像c#这样的强类型语言中,这可能是一个问题,但我不确定这是否成立。在调试器中测试它是否按预期工作。

Would the same be true in python? Should this property really be a method? I can see how in a strongly typed language such as c# this could be an issue but am not really sure if the holds true here. Testing in the debugger it works as expected.

要清楚,我正在测试以下内容。

To be clear I am testing something like the following.

class A(object):
    def __init__(self):
        self.__x = None

    @property
    def x(self):
        if not self.__x:
            self.__x = calculate_x()
            if not some_test(self.__x):
                # Is this a bad idea?
                raise ValueError('Get x error {}'.format(self.__x))
        return self.__x

    @x.setter
    def x(self, value):
        if not some_test(value):
            raise ValueError('Set x error {}'.format(value))
        self.__x = value

我去过RTFM,并且有很多关于房地产的知识,但是似乎看不到任何使用它或警告它的东西。这是完全可以接受的,还是我从地狱创建了某种可怕的反模式?

I have been RTFM and a lot about properties but can't seem to see anything that either uses it or else warns against it. Is this all perfectly acceptable or have I created some kind of monstrous antipattern from hell?

之所以这样做,是因为我想到了类似惰性描述符的内容,该描述符可以让我快速标记属性。例如

The reason I am trying this is because I was think of something like a "lazy" descriptor that allows me to quickly markup properties. e.g.

from functools import wraps

    class Descriptor(object):
        def __init__(self, func):
            self.func = func
        def __get__(self, obj, type=None):
            value = self.func(obj)
            setattr(obj, self.func.__name__, value)
            return value

    def lazy(func):
        return wraps(func)(Descriptor(func))

然后

class A(object):
    def __init__(self):
        self.__x = None

    @lazy
    def x(self):
        # where calculate_x might raise an exception
        return calculate_x()


推荐答案

更多阅读并返回本文之后,我将回答我自己的问题,并说不-根据PEP 8样式指南,不建议这样做。

After more reading and coming back to this I am going to answer my own question and say no - this is not recommended based on the PEP 8 Style Guide.

https://www.python.org/dev/peps/pep -0008 /

Note 3: Avoid using properties for computationally expensive operations;
the attribute notation makes the caller believe that access is (relatively) 
cheap.

我意识到这在某种程度上解释了克里斯蒂安的答案-但我在寻找某种官方文档或指南在这种模式上。

I realise this is paraphrasing Christian's answer somewhat - but I was looking for some kind of official documentation or guidance on this kind of pattern.

这篇关于通过设计,属性获取器是否应该在python中引发异常?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆