洗牌对象列表
我有一个在Python中的对象的列表,我想打乱他们。 我以为我可以使用random.shuffle
方法,但是当列表是对象时,这似乎失败了。 有没有一种方法来洗牌对象或其他方式呢?
import random class a: foo = "bar" a1 = a() a2 = a() b = [a1,a2] print random.shuffle(b)
这将失败。
random.shuffle
应该工作。 下面是一个例子,其中的对象是列表:
from random import shuffle x = [[i] for i in range(10)] shuffle(x) # print x gives [[9], [2], [7], [0], [4], [5], [3], [1], [8], [6]] # of course your results will vary
请注意,洗牌工作到位 ,并返回None。
正如你所了解的,就地洗牌是个问题。 我也经常遇到问题,而且似乎也经常忘记如何复制一个列表。 使用sample(a, len(a))
是解决scheme,使用len(a)
作为样本大小。 请参阅https://docs.python.org/3.6/library/random.html#random.sample Python文档。
这是一个简单的版本,使用random.sample()
,将混洗结果作为新列表返回。
import random a = range(5) b = random.sample(a, len(a)) print a, b, "two list same:", a == b # print: [0, 1, 2, 3, 4] [2, 1, 3, 4, 0] two list same: False # The function sample allows no duplicates. # Result can be smaller but not larger than the input. a = range(555) b = random.sample(a, len(a)) print "no duplicates:", a == list(set(b)) try: random.sample(a, len(a) + 1) except ValueError as e: print "Nope!", e # print: no duplicates: True # print: Nope! sample larger than population
#!/usr/bin/python3 import random s=list(range(5)) random.shuffle(s) # << shuffle before print or assignment print(s) # print: [2, 4, 1, 3, 0]
我花了一些时间才得到这个,但洗牌文件非常清晰:
随机播放列表x; 返回无。
所以你不应该print random.shuffle(b)
但是random.shuffle(b)
而不是print b
。
>>> import random >>> a = ['hi','world','cat','dog'] >>> random.shuffle(a,random.random) >>> a ['hi', 'cat', 'dog', 'world']
它对我来说工作正常。 确保设置随机方法。
如果你碰巧正在使用numpy(非常stream行的科学和金融应用),你可以节省自己的import。
import numpy as np np.random.shuffle(b) print(b)
http://docs.scipy.org/doc/numpy/reference/generated/numpy.random.shuffle.html
'print func(foo)'将在用'foo'调用时打印'func'的返回值。 'shuffle'然而没有None作为它的返回types,因为这个列表将被修改,因此它不会打印任何东西。 解决方法:
# shuffle the list in place random.shuffle(b) # print it print(b)
如果您更多地使用函数式编程风格,您可能需要使用以下包装函数:
def myshuffle(ls): random.shuffle(ls) return ls
from random import random my_list = range(10) shuffled_list = sorted(my_list, key=lambda x: random())
这个替代方法对于你想交换sortingfunction的一些应用程序可能是有用的。
我们可以定义一个叫做shuffled
的函数( sort
和sort
一样)
def shuffled(x): import random y = x[:] random.shuffle(y) return y x = shuffled([1, 2, 3, 4]) print x
在某些情况下,当使用numpy数组时,使用random.shuffle
在数组中创build重复的数据。
另一种方法是使用numpy.random.shuffle
。 如果你正在使用numpy,这是通用random.shuffle
的首选方法。
numpy.random.shuffle
例
>>> import numpy as np >>> import random
使用random.shuffle
:
>>> foo = np.array([[1,2,3],[4,5,6],[7,8,9]]) >>> foo array([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) >>> random.shuffle(foo) >>> foo array([[1, 2, 3], [1, 2, 3], [4, 5, 6]])
使用numpy.random.shuffle
:
>>> foo = np.array([[1,2,3],[4,5,6],[7,8,9]]) >>> foo array([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) >>> np.random.shuffle(foo) >>> foo array([[1, 2, 3], [7, 8, 9], [4, 5, 6]])
如果您有多个列表,则可能需要先定义排列(清单/重新排列列表中的项目),然后将其应用于所有列表:
import random perm = list(range(len(list_one))) random.shuffle(perm) list_one = [list_one[index] for index in perm] list_two = [list_two[index] for index in perm]
Numpy / Scipy
如果你的列表是numpy数组,则更简单:
import numpy as np perm = np.random.permutation(len(list_one)) list_one = list_one[perm] list_two = list_two[perm]
def shuffle(_list): if not _list == []: import random list2 = [] while _list != []: card = random.choice(_list) _list.remove(card) list2.append(card) while list2 != []: card1 = list2[0] list2.remove(card1) _list.append(card1) return _list
确保你没有命名你的源文件random.py,并且你的工作目录中没有一个名为random.pyc的文件。或者可能导致你的程序尝试导入你的本地random.py文件而不是python的随机模块。
你可以去这个:
>>> A = ['r','a','n','d','o','m'] >>> B = [1,2,3,4,5,6] >>> import random >>> random.sample(A+B, len(A+B)) [3, 'r', 4, 'n', 6, 5, 'm', 2, 1, 'a', 'o', 'd']
如果你想返回到两个列表,然后你把这个长列表分成两个。
你可以build立一个函数,它将一个列表作为参数,并返回列表的一个混洗版本:
from random import * def listshuffler(inputlist): for i in range(len(inputlist)): swap = randint(0,len(inputlist)-1) temp = inputlist[swap] inputlist[swap] = inputlist[i] inputlist[i] = temp return inputlist
洗牌过程是“与replace” ,所以每个项目的发生可能会改变! 至less当你的列表中的项目也是列表。
例如,
ml = [[0], [1]] * 10
后,
random.shuffle(ml)
[0]的数目可以是9或8,但不完全是10。
计划:写出洗牌,而不依靠图书馆做繁重的工作。 例子:从元素0开始,从头开始; 为它find一个新的随机位置,比如6,将0的值设置为6,将6的值设置为0.移至元素1并重复此过程,依此类推至列表的其余部分
import random iteration = random.randint(2, 100) temp_var = 0 while iteration > 0: for i in range(1, len(my_list)): # have to use range with len() for j in range(1, len(my_list) - i): # Using temp_var as my place holder so I don't lose values temp_var = my_list[i] my_list[i] = my_list[j] my_list[j] = temp_var iteration -= 1
它工作正常。 我在这里用函数作为列表对象来尝试它:
from random import shuffle def foo1(): print "foo1", def foo2(): print "foo2", def foo3(): print "foo3", A=[foo1,foo2,foo3] for x in A: x() print "\r" shuffle(A) for y in A: y()
它打印出来:foo1 foo2 foo3 foo2 foo3 foo1(最后一行的foos有一个随机顺序)