【问题标题】:python passing by referencepython通过引用传递
【发布时间】:2017-07-29 08:46:15
【问题描述】:

今天当我做这样的事情时发生了奇怪的事情:

a = np.array([1, 2, 3])

b = a

b[0] = 0

print a, b

然后值好像是通过引用传递的!答案变成:

result: [0 2 3] [0 2 3]

但通常我认为python中的变量是按值传递的,像这样:

a = np.array([1, 2, 3])

b = a

b = np.array([0, 2, 3])

print a, b

然后答案就变成了:

result: [1 2 3] [0 2 3]

但是为什么会这样呢?如何确定变量是通过引用传递还是通过值传递?有人说这是因为可变对象,但我还是不太明白。那你能给我解释一下吗?非常感谢!

【问题讨论】:

  • 你觉得这有什么奇怪的?
  • 作业 从不 在 Python 中复制。它总是这样工作的。您的第二个示例与您的第一个示例完全相同
  • 在第二种情况下,您将新对象np.array([0, 2, 3]) 分配给b,而不是更改原始对象。更具体地说,如果你在第二种情况下写b = Noneb = 10,它不会对a产生任何影响,这是合理的。
  • 另外,这不是关于评估策略,而是关于分配在 Python 中的工作方式。阅读Python has names, not variables。另外,请查看Facts and Myths about Python Names and Values

标签: python python-2.7 pass-by-reference


【解决方案1】:

由于它与 NumPy 没有直接关系,我们将其重写为:

a = [1, 2, 3]

b = a

b = [0, 2, 3]

print a, b

关键是名称和值是分开的。所以在第一行:

a = [1, 2, 3]

您创建一个列表并将其分配给a

现在在下一行将a 分配给b。仍然只有 1 个列表,两个名称都只是引用它。

接下来创建一个新列表并将其分配给b。现在b 指的是新列表而不是 old 列表。反过来,现在只有 1 个名称 (a) 引用另一个列表,而不是 2 个名称。

因此,如果我们以第一个示例为例,您在哪里:

b[0] = 0

ab 都引用同一个列表,因此可以从两个名称中观察到变化,因为两个名称都引用同一个列表。

【讨论】:

    【解决方案2】:

    Python 中的变量赋值始终是对引用的赋值。换句话说,在 Python 中,变量就是名称,而分配一个变量就是为某物声明一个名称。

    a = np.array([1, 2, 3])
    
    b = a
    
    b[0] = 0
    
    print a, b
    

    这意味着让a 成为第一个数组的名称,然后让b 成为a 的名称,但a 表示第一个数组,所以实际上我们只是说让b也是第一个数组的名称。然后b[0] = 0 表示更改数组的第一个元素。然后,当您打印 ab 时,您将打印两次相同的东西(数组),因为 ab 是相同的东西的名称。

    a = np.array([1, 2, 3])
    
    b = a
    
    b = np.array([0, 2, 3])
    
    print a, b
    

    前两行与上次相同。 a 是数组的名称,b 也是如此。那么b = np.array([0, 2, 3]) 意味着b 现在是这个新数组的名称。因此,当您打印ab 时,您将打印a,它仍然是第一个数组的名称,而b,它是第二个数组的名称。

    【讨论】:

      猜你喜欢
      • 2020-12-06
      • 1970-01-01
      • 2017-08-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-01-12
      相关资源
      最近更新 更多