【问题标题】:Having problems with python's random.shufflepython的random.shuffle有问题
【发布时间】:2023-04-04 12:15:01
【问题描述】:

我想制作一个矩阵,其线是以下向量的不同排列=
[1,2,3,4,5,10,10,10,10,10]
我尝试使用 random.shuffle 函数,但似乎每次我使用它时,它都会重新定义分配给它的所有对象。例如,我尝试了以下方法:

vec=[1,2,3,4,5]  
for i in range(5):  
    vec.append(10)  
Matpreferences=[]  
for i in range(10):  
    random.shuffle(vec)  
    Matpreferences.append(vec)  

然后我得到一个所有行都相等的矩阵。
例如:

[0, 0, 1.0, 0, 2.0, 3.0, 0, 0.5, 2.5, 1.5, 0]    
[0, 0, 1.0, 0, 2.0, 3.0, 0, 0.5, 2.5, 1.5, 0]  
[0, 0, 1.0, 0, 2.0, 3.0, 0, 0.5, 2.5, 1.5, 0]  
[0, 0, 1.0, 0, 2.0, 3.0, 0, 0.5, 2.5, 1.5, 0]    
...

我什至尝试过类似的东西

Matpreferences=[]  
    for i in range(10):  
    random.shuffle(vec)
    a=vec
    Matpreferences.append(a)   

但它会产生相同的结果。有什么简单的方法可以解决这个问题吗?
非常感谢您提供的任何帮助 =)

【问题讨论】:

  • 非常感谢大家,所有的答案都很棒。我不精通计算机科学,所以我不知道设置 v=vec 或 v=vec[:] 会有所不同

标签: python matrix random permutation shuffle


【解决方案1】:

您向列表添加对象引用。把它想象成一个指针。您添加到 Matpreferences 的每个 vec 都指向同一个实例。

看这个例子:

>>> vec = [1,2,3,4,5]
>>> vec2 = vec
>>> random.shuffle(vec)
>>> print vec
[2, 4, 3, 1, 5]
>>> print vec2
[2, 4, 3, 1, 5]
>>> 

如你所见,vecvec2 的内容是相同的,即使我没有洗牌 vec2

您需要做的是将vec的内容复制到一个新列表中,然后将该列表添加到Matpreferences

将最后一行替换为

Matpreferences.append([x for x in vec])

Matpreferences.append(vec[:])

【讨论】:

    【解决方案2】:

    在随机播放之前,您需要复制vec

    import random
    vec=[1,2,3,4,5]
    for i in range(5):
        vec.append(10)
    Matpreferences=[]
    for i in range(10):
        v = vec[:]
        random.shuffle(v)
        Matpreferences.append(v)
    

    说明

    来自您的代码:

    a=vec
    Matpreferences.append(a)  
    

    这里,a 指向的数据与 vec 指向的数据相同。因此,当a 被洗牌时,vec 和所有指向vec 的东西也是如此。

    相比之下,由于下标[:],这段代码创建了一个新的独立数据副本:

    v = vec[:]
    

    因为v是一个独立的独立副本,所以洗牌vvec没有影响。

    【讨论】:

      【解决方案3】:

      random.shuffle 将列表打乱,因此每次调用后,vec 的内容都会被打乱。请注意,vec 是对列表的引用,因此当您在列表中附加 vec 10 次时,它会包含 10 次相同的引用。他们都持有相同的清单。这就是为什么您会看到相同的列表。 vec 确实洗了 10 次,但是打印出来的时候只能看到最后一个排列。

      要解决此问题,您需要每次制作一个新的 vec 副本,将副本打乱并将其附加到 Matpreferences。或者您可以随机播放vec,然后将其副本附加到Matpreferences

      复制一个列表很容易,我认为最短的一个是使用切片:

      Matpreferences.append(vec[:])
      

      【讨论】:

        猜你喜欢
        • 2018-05-11
        • 1970-01-01
        • 1970-01-01
        • 2014-12-22
        • 2019-04-22
        • 1970-01-01
        • 1970-01-01
        • 2018-01-10
        • 1970-01-01
        相关资源
        最近更新 更多