在这种情况下,如何平衡“Python”和“方便”?

2024-09-30 06:13:41 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个将由客户端代码实现的“接口”:

class Runner:
    def run(self):
        pass

run通常应该返回一个docutilsnode,但是因为最远的 常见的情况是纯文本,调用方允许run返回一个字符串,这将是 使用type()检查并转换为node。在

不过,按照我对“Python”的理解,这不是“Python”的原因 检查某个东西的type()并不会让它“表现”为一个类型 一种——即“Pythonic”代码应该使用duck类型。在

我考虑过了

^{pr2}$

我不在乎这个类型,但我不在乎 就在名字里,这让人分心。在

有什么我错过的想法吗?还有,我可能会遇到什么问题吗 在我的“坏”系统下(对我来说,它或多或少是安全的)?在


Tags: run字符串代码文本selfnode客户端类型
3条回答

查看Errors and Exceptions.您可以这样做:

def run(self,arg):
    try:
        return make_node(arg)
    except AlreadyNodeError:
        pass

在make_node函数中,如果参数已经是节点,则让它引发AlreadyNodeError。在

我认为这是一个有点欺骗性的例子;有些事情你还没有说。我猜,当你说你“有一个接口”时,你的意思是你有一些代码接受一个对象并调用它的run方法。在

如果在调用该对象的run方法之前没有测试该对象的类型,那么您使用的是duck类型,简单明了!(在本例中,如果它有一个run方法,那么它就是一个Runner)只要你不在对象上使用type或{},那么你就是python了。在

是接受纯字符串还是只接受节点对象的问题是一个微妙的不同问题。字符串和node对象可能根本没有实现相同的接口!字符串基本上不会像node那样呱呱叫,所以你不必把它们当作一个。这就像大象来了,如果你想让它像鸭子一样嘎嘎叫,你必须给大象一个磁带播放器,并训练大象先使用它。在

所以这不再是“鸭子类型”的问题,而是界面设计的问题。你正试图决定你希望你的接口有多严格。在

为了给你一个答案,那么,在这个层次上,我认为假设run返回一个node对象是最具python风格的。不需要使用isinstancetype来测试。假设它是一个node对象,如果使用你的接口的程序员弄错了,并且看到了一个异常,那么他们必须读取你的docstring,这将告诉他们run应该传递一个node对象。在

然后,如果您希望也接受字符串或类似字符串的东西,您可以这样做。由于字符串是相当原始的类型,我想说使用isinstance(obj, basestring)(但是不是type(obj) == str,因为它拒绝unicode字符串,等等)。本质上,这就是你对你的程序的懒惰用户非常宽容和友好;你已经超越了接受大象和像鸭子一样呱呱叫的东西。在

(更具体地说,我想说这有点像在函数的开头调用iter来同时接受生成器和序列)

您不一定需要有方法来处理每种类型,特别是如果只需要简单的操作就可以了。一种常见的Python式方法是:

def run(self):
    try:
        ...assume it's a str   
    except TypeError:
        ...oops, not a str, we'll address that

这遵循了Easier to ask for forgiveness than permission (EAFP)风格的编码,通常更快更简单。在

相关问题 更多 >

    热门问题