在这种情况下我应该更喜欢 'asking for permission' 吗?

Should I prefer 'asking for permission' in this case?

在我的函数中,我期待一个可能是 tuplestr 的参数。作为 Python 的新手,我了解到 'begging forgiveness' 优于 'asking for permission'。所以我没有检查参数的类型,而是这样做:

def f(a):
    try:  # to handle as tuple
        e1, e2, e3 = a
        ...
    except ValueError:  # unpacking failed, so must be a string.
        pass
    # handle as string

但是,这并不总是有效。如果 a 是长度 3str 怎么办?代码会将其视为元组。

遇到这种情况怎么办?求助于类型检查?是不是少了'Pythonic'?请解释最'Pythonic'的解决方案及其原因。

显式优于隐式:定义两个函数,一个用于元组,另一个用于字符串。第二个最佳选择是,让一个函数具有三个参数,其中两个是可选的:

def f(e1, e2=None, e3=None):
    if e2 is None and e3 is None:
        # a string
    else:
        # three strings

最小最好的可能性是检查参数的类型:

def f(a):
    if isinstance(a, basestring):
        # a string
    else:
        # perhaps a tuple

Python 具有 isinstance() 功能是有原因的。有时检查参数的类型是正确的做法;在这里完全可以接受。

在 Python 中进行类型检查是完全没问题的,尤其是当您出于函数重载的目的而这样做时。

但我建议您对字符串而不是元组进行类型检查。虽然看起来你总是传递一个元组,但在很多情况下传递不同的序列也可能很有意义,例如列表也非常好。

所以你应该保留逻辑原样,但首先检查字符串输入:

def f(a):
    if isinstance(a, str): # in Python 2, check against `basestring`
        # handle as string
        # …
    else:
        # handle as tuple
        e1, e2, e3 = a
        # …

这样你就会得到一个正确的异常冒泡,以防解包没有正确成功,例如,如果有人传递一个 2 元素元组。在您的原始代码中,您必须自己以某种方式处理它(以避免 运行 认为它是字符串的代码)。