Python副作用我不知道';我不明白

Python副作用我不知道';我不明白,python,side-effects,Python,Side Effects,如果我运行它,我将看到在第一个递归中,Testprint行生成与这里的Testprint行不同的值。为什么?此代码如何影响组的值?在测试值失败的情况下,我试图将一个未更改的group传递到下一个递归级别的group\u move,但在我进行任何递归调用之前,group似乎受到了某种影响。上述内容与此有何不同: def group_move(group, damper): # Make a copy to test values new = group # See wha

如果我运行它,我将看到在第一个递归中,
Test
print行生成与这里的
Test
print行不同的值。为什么?此代码如何影响
组的值?在测试值失败的情况下,我试图将一个未更改的
group
传递到下一个递归级别的
group\u move
,但在我进行任何递归调用之前,
group
似乎受到了某种影响。上述内容与此有何不同:

def group_move(group, damper):
    # Make a copy to test values
    new = group

    # See what the original group value is
    print("Test = " + str(group.ctris[0].p1.x))
    dr = some float
    dx = some float
    dy = some float
    # Make changes to new
    moveGroup(new, dr, dx, dy)
    # See if those changes produce allowed values
    if (off_board_check(new) == 1):
        damper += 2.0
        # Reset to original to try again
        print("Test Here = " + str(group.ctris[0].p1.x))
        group_move(group, damper)
    else:
        # If everything is on the board, then make the change
        group = new
评论是不正确的。那不是复制品。所做的只是使名为
new
的变量指向
group
所指向的同一对象

如果要创建实际副本,可能需要查看。

# Make a copy to test values
new = group
您正在复制对象的引用

此外,您的测试不是“智能”测试,因为在您的示例中,您使用的是基本类型变量,而不是对象

一般来说,记住

Python中的赋值语句不复制对象,而是在目标和对象之间创建绑定对于可变或包含可变项的集合,有时需要一个副本,以便可以更改一个副本而不更改另一个副本。此模块提供一般的浅拷贝和深拷贝操作(解释如下)

这意味着“
new
应为表达式
评估结果的名称(即当前由
命名的对象,因为表达式只是一个名称)”。这是一个别名,不是副本

new = group

这里也一样<代码>x=1;y=x
使它们都引用表示整数的对象
1
x=7
导致
x
停止引用
1
对象,并开始引用表示整数
7
的另一个对象。同样适用于
y=77
。独立性不是因为任何复制(因为没有复制),而是因为代码中没有指定对所引用对象的更改(这在Python中对于
int
s实际上是不可能的)。当人们期望这段代码的结尾x等于77时,他们实际上是在不一致地解释事物,在某些行上期望值语义,在其他行上期望引用语义值语义和引用语义都预测实际结果

是的,但这是因为您使用的是无法更改的简单值类型-
1
7
,等等(您无法重新定义
1
的值)。另一方面,对象是所谓的“引用类型”——包含它们的变量实际上并不包含对象,而是对对象的引用。因此,赋值不会创建对象的副本,而只创建引用的副本。。。它仍然指向同一个对象。您添加的示例处理不可变类型(int),您无法更改它们,因此赋值看起来像一个副本,但不是。您没有更改对象,而是更改名称绑定到的对象。举个简单的例子,请在python解释器中尝试:
a=[]
b=a
a.append('foo')
b
@Amber:python中没有值类型。一切都是对象。这是一个INT不可变的问题,赋值重新绑定引用而不是改变引用。“如果它执行任意数量的递归,那么它将返回一个NoneType!?”,因为您不会传播递归调用返回的结果。Python具有足够的“命令性”,因此
return
的工作方式与命令式语言中的工作方式相同。
# Make a copy to test values
new = group
new = group
x = 1
y = x
x = 7
y = 77