简体   繁体   English

非常奇怪的Python变量作用域行为

[英]Very weird Python variable scope behaviour

I'm having a problem with Python 2.7 that is driving me insane. 我在Python 2.7中遇到问题,这使我发疯。

I'm passing an array to some functions and altough that variable is suposed to be local, in the end the value of the variable inside main is changed. 我将数组传递给某些函数,但该变量被认为是局部变量,最后main内部的变量值被更改。

I'm a bit new to Python, but this goes against any common sense I got. 我对Python有点陌生,但这违背了我的任何常识。

Any ideas of what I'm doing wrong? 关于我在做什么错的任何想法?

def mutate(chromo):
    # chooses random genes and mutates them randomly to 0 or 1
    for gene in chromo:
        for codon in gene:
            for base in range(2):
                codon[randint(0, len(codon)-1)] = randint(0, 1)
    return chromo

def mate(chromo1, chromo2):
    return mutate([choice(pair) for pair in zip(chromo1, chromo2)])


if __name__ == '__main__':
    # top 3 is a multidimensional array with 3 levels (in here I put just 2 for simplicity)
    top3 = [[1, 0], [0, 0], [1, 1]]

    offspring = []
    for item in top3:
        offspring.append(mate(top3[0], item))

    # after this, top3 is diferent from before the for cycle

UPDATE Because Python passes by reference, I must make a real copy fo the arrays before using them, so the mate functions must be changed to: 更新因为Python通过引用传递,所以在使用数组之前必须对数组进行真实复制,因此必须将mate函数更改为:

import copy
def mate(chromo1, chromo2):
    return mutate([choice(pair) for pair in zip(copy.deepcopy(chromo1), copy.deepcopy(chromo2))])

The problem you are having is stemming from the fact that arrays and dictionaries in python are passed by reference. 您遇到的问题源于python中的数组和字典通过引用传递的事实。 This means that instead of a fresh copy being created by the def and used locally you are getting a pointer to your array in memory... 这意味着您将获得指向内存中数组的指针,而不是由def创建并在本地使用的新副本。

x = [1,2,3,4]

def mystery(someArray):
     someArray.append(4)
     print someArray

mystery(x)
[1, 2, 3, 4, 4]

print x
[1, 2, 3, 4, 4]

You manipulate chromo , which you pass by reference. 您可以操作chromo ,您可以通过引用传递它。 Therefore the changes are destructive... the return is therefore kind of moot as well ( codon is in gene and gene is in chromo ). 因此,改变是破坏性的...的return ,因此是一种没有实际意义,以及( codon是在genegenechromo )。 You'll need to make a (deep) copy of your chromos , I think. 我认为,您需要复制(深层) chromos

try changing 尝试改变

offspring.append(mate(top3[0], item)) to offspring.append(mate(top3[0][:], item[:])) offspring.append(mate(top3 [0],item))到offspring.append(mate(top3 [0] [:],item [:]))

or use the list() function 或使用list()函数

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM