【问题标题】:Python tuple ... is not a tuple? What does the comma do?Python 元组...不是元组吗?逗号有什么作用?
【发布时间】:2016-12-09 19:17:17
【问题描述】:

我正在查看课程材料中的代码,不得不编写一个函数,将值 99 添加到 listtuple。最终代码如下所示:

def f(l):
    print(l)
    l += 99,
    print(l)

f([1,2,3])
f((1,2,3))

这是用来展示一些不同的东西,但我有点挂断了l += 99,。这样做的目的是创建一个包含 99 和 list 以及 tuple 的可迭代对象,支持简单“添加”此类对象以创建新实例/添加新元素。

我真正不明白的是使用语法element, 创建的究竟是什么?如果我执行x = 99, 之类的任务,type(x) 将是tuple,但如果我尝试运行x = tuple(99),它将失败,因为 99 不可迭代。也有:

  • 使用语法element,创建的某种中间可迭代对象?
  • 是否定义了一个特殊函数,允许在没有迭代的情况下调用 tuple,并且以某种方式将 , 映射到该函数?

编辑: 万一有人想知道为什么接受的答案是这个答案:我的第二个问题的解释做到了。我应该对我的问题更清楚,但 += 实际上让我感到困惑,这个答案包括关于此的信息。

【问题讨论】:

  • @ScottHunter x = 99,,而不是 x = 99; 逗号与分号
  • 这个问题实际上发现了一些我以前不知道的东西。显然list.__add__ 方法(用于添加)不会接受tuple 用于other 参数,但list.__iadd__(用于+=)确实接受它。我想知道这是为什么?
  • 这闻起来像个虫子@RickTeachey
  • @RickTeachey 我会看看能否在错误跟踪器和/或源代码上找到任何东西,这也让我感到非常惊讶。编辑:Found it :-)
  • @JimFasarakis-Hilliard “这种情况已经很久了,Guido 说他不会再这样做了(这是他的遗憾清单)。但是,我们不会破坏代码通过更改它(list.__iadd__ 像 list.extend 一样工作)。”懦夫! ;)

标签: python python-3.x tuples


【解决方案1】:

如果= 的左侧参数是一个简单名称,则绑定到该名称的参数类型当前 是无关紧要的。 tuple(99) 失败,因为 tuple 的参数不可迭代;它与x 是否已经引用tuple 的实例无关。

99, 创建一个带有单个参数的元组;括号仅用于将其与逗号的其他用途分开。例如,foo((99,100)) 使用单个元组参数调用 foo,而 foo(99,100) 使用两个不同的 int 参数调用 foo

【讨论】:

    【解决方案2】:

    语法element, 只是创建一个“中间”tuple,而不是其他类型的对象(尽管tuple 当然是可迭代的)。

    但是,有时您需要使用括号以避免歧义。出于这个原因,你会经常看到这样的:

    l += (99,)
    

    ...即使括号在语法上不是必需的。我也碰巧认为这更容易阅读。但是括号在您已经发现的其他情况下在语法上是必需的:

    list((99,))
    tuple((99,))
    set((99,))
    

    您也可以这样做,因为[] 会生成list

    list([99])
    tuple([99])
    set([99])
    

    ...但是您不能这样做,因为在这些情况下 99, 不是 tuple 对象:

    list(99,)
    tuple(99,)
    set(99,)
    

    要回答您的第二个问题,不,没有办法使 tuple() 函数接收不可迭代。事实上,这就是element,(element,) 语法的目的——非常类似于[] 用于list{} 用于dictset(因为listdict,和set 函数也都需要可迭代参数):

    [99] #list 
    (99,) #tuple -  note the comma is required
    {99} #set
    

    正如问题 cmets 中所讨论的,令人惊讶的是,您可以使用 tuple 对象增加 (+=) list。请注意,您不能这样做:

    l = [1]  
    l + (2,) # error
    

    这是不一致的,所以是probably something that should not have been allowed。相反,您需要执行以下操作之一:

    l += [2]
    l += list((2,))
    

    但是,修复它会给人们带来问题(更不用说消除邪恶计算机科学教授利用混淆的成熟机会),所以他们没有。

    【讨论】:

      【解决方案3】:

      元组构造函数需要一个可迭代对象(就像它在您的错误消息中所说的那样),因此为了执行x = tuple(99),您需要将它包含在一个像列表一样的可迭代对象中:

      x = tuple([99])
      

      x = tuple((99,))
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-05-16
        • 2011-06-17
        • 1970-01-01
        • 2015-09-26
        • 1970-01-01
        • 2023-01-31
        • 2019-01-14
        • 1970-01-01
        相关资源
        最近更新 更多