0

我认为传递给 python 函数的变量的更改保留在函数的本地范围内,而不是传递到全局范围内。但是当我写一个测试脚本时:

#! /usr/bin/python
from numpy import *

def fun(box, var):
    box[0]=box[0]*4
    var=var*4
    return 0

ubox,x = array([1.]), 1.
print ubox,x
fun(ubox,x)
print ubox,x

输出是:

[myplay4]$ ./temp.py 
[ 1.] 1.0
[ 4.] 1.0

整数变量 x 不受函数内部操作的影响,但数组受。列表也会受到影响,但这只发生在对列表/数组切片而不是对单个元素进行操作时。

谁能解释为什么在这种情况下本地范围会传递给全局范围?

4

4 回答 4

2

在你的功能

def fun(box, var):
    box[0]=box[0]*4
    var=var*4
    return 0

两者boxvar都是本地的,并且更改它们不会更改它们在调用范围内的值。但是,这一行:

box[0]=box[0]*4

不改变boxbox它改变了引用的对象。如果那行写成

box = box[0]*4 + box[1:]

那么box在调用范围内确实会保持不变。

于 2013-01-26T19:45:53.047 回答
2

要意识到的重要一点是,当将对象传递给函数时,该函数不能与该对象的独立副本一起使用,它与同一个对象一起使用。因此,对对象的任何更改对外部都是可见的。

您说对局部变量的更改仍然是局部的。这是真的,但它只适用于改变变量(即重新分配它们)。它不适用于改变变量指向的对象。

在您的示例中,您 reassign var,因此更改在外部不可见。但是,您正在变异box(通过重新分配其元素之一)。这种变化在外部是可见的。如果您只是简单地重新分配box以引用不同的对象 ( box = something),则该更改不会在外部可见。

于 2013-01-26T19:48:18.297 回答
1

这与范围完全无关。

您正在将一个对象传递给一个函数。在该函数内部,该对象发生了变异。关键是函数内部的变量与调用函数中引用的对象相同,因此更改在外部可见。

于 2013-01-26T19:43:22.990 回答
-2

这不取决于范围。这取决于 Python 如何复制对象。在这方面,存在三种对象:标量、可变对象、不可变对象。

标量是按值复制的,可变对象是按引用复制的,不可变对象可能是按引用复制的,但是由于您无法修改它们,因此没有任何含义。

例如,标量是所有数字类型。不可变的有:字符串和元组。可变的有:列表、字典和其他对象。

于 2013-01-26T19:48:20.193 回答