【问题标题】:Function in Python Setting Global Variables (without intent)Python中的函数设置全局变量(无意)
【发布时间】:2017-08-07 23:40:03
【问题描述】:

我不知道这是否是其他人遇到的问题,但我在 python 中有这样的代码:

def makemove(board,move,val):
    new=board
    new[move[0]][move[1]]=val
    return new

我的问题是,如果我通过简单地执行 makemove(game,[0,1],-1) 来使用此功能,其中游戏等于 [[0,0,1],[0,1,0],[1 ,0,0]] 变量 game 变为 [[0, -1, 1], [0, 1, 0], [1, 0, 0]]。

我试图研究设置全局变量的函数,但因此我没有找到阻止 makemove() 设置您放入其中的变量的方法。我有什么明显的遗漏吗?

【问题讨论】:

    标签: function python-3.x variables


    【解决方案1】:

    你需要克隆board

    import
    new = copy.deepcopy(board)
    

    请参阅https://stackoverflow.com/a/2612815/93910 了解其他方法。

    您的代码设置了作为“参考”的变量的元素。 换句话说,您的变量new 实际上是对board 的数组引用,即它指向同一个内存位置。所以当你改变new时,原来的变量board就会改变。

    这是关于如何考虑这个问题的另一个答案:https://stackoverflow.com/a/9697367/93910

    【讨论】:

    • 我试过了,它有效,但为什么没有“新”变量就不好?
    【解决方案2】:

    这基本上是因为 Python 中的赋值并不像你想象的那样,列表是可变序列

    列表是 Python 对象。 name board 只是该对象的标签引用。 因此,当您说 new=board 时,这意味着“让名称 new 引用与名称 board 相同的对象”。

    在 Python 中,每个对象都有一个唯一标识符,您可以使用 id() 检索该标识符。让我们创建一个板,完成任务,看看会发生什么:

    In [1]: board = [[0,0,1],[0,1,0],[1,0,0]]
    
    In [2]: new = board
    
    In [3]: id(new), id(board)
    Out[3]: (34495504136, 34495504136)
    

    newboard 引用同一个对象。

    由于列表是可变序列,因此您可以更改它而不会出错。

    因此,如果您想在函数中使用任何可变序列而不修改原始序列,则应先使用copy.deepcopy 进行复制并对其进行修改。

    【讨论】:

    • 那么在我的代码中,板子是否也会引用(或具有相同的 id)作为我插入的变量?
    • @NathanEaves 是的。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-21
    • 2012-05-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多