原文:
一、fisher–yates shuffle
演算法思想就是從原始陣列中隨機抽取乙個新的數字到新陣列中。
#fisher–yates shuffle
''' 1. 從還沒處理的陣列(假如還剩k個)中,隨機產生乙個[0, k]之間的數字p(假設陣列從0開始);
2. 從剩下的k個數中把第p個數取出;
3. 重複步驟2和3直到數字全部取完;
4. 從步驟3取出的數字序列便是乙個打亂了的數列。
'''import random
def shuffle(lis):
result =
while lis:
p = random.randrange(0, len(lis))
lis.pop(p)
return result
r = shuffle([1, 2, 2, 3, 3, 4, 5, 10])
print(r)
二、knuth-durstenfeld shuffle(random.shuffle)
每次從未處理的資料中隨機取出乙個數字,然後把該數字放在陣列的尾部,即陣列尾部存放的是已經處理過的數字。這是乙個原地打亂順序的演算法,演算法時間複雜度也從fisher演算法的o(n2)提公升到了o(n)。
#knuth-durstenfeld shuffle
def shuffle(lis):
for i in range(len(lis) - 1, 0, -1):
p = random.randrange(0, i + 1)
lis[i], lis[p] = lis[p], lis[i]
return lis
r = shuffle([1, 2, 2, 3, 3, 4, 5, 10])
print(r)
三、inside-out algorithm
inside-out algorithm 演算法的基本思想是設一游標i從前向後掃瞄原始資料的拷貝,在[0, i]之間隨機乙個下標j,然後用位置j的元素替換掉位置i的數字,再用原始資料位置i的元素替換掉拷貝資料位置j的元素。其作用相當於在拷貝資料中交換i與j位置處的值。
#inside-out algorithm
def shuffle(lis):
result = lis[:]
for i in range(1, len(lis)):
j = random.randrange(0, i)
result[i] = result[j]
result[j] = lis[i]
return result
r = shuffle([1, 2, 2, 3, 3, 4, 5, 10])
print(r)
01揹包及空間優化: 洗牌演算法shuffle
對這個問題的研究始於一次在群裡看到朋友發的洗牌面試題。當時也不知道具體的解法如何,於是隨口回了一句 每次從剩下的數字中隨機乙個。過後找相關資料了解了下,洗牌演算法大致有3種,按發明時間先後順序如下 一 fisher yates shuffle 演算法思想就是從原始陣列中隨機抽取乙個新的數字到新陣列中...
三種洗牌演算法shuffle
由抽牌 換牌和插牌衍生出三種洗牌演算法,其中抽牌和換牌分別對應fisher yates shuffle和knuth durstenfeld shhuffle演算法。最早提出這個洗牌方法的是 ronald a.fisher 和 frank yates,即 fisher yates shuffle,其基...
go實現陣列切片洗牌函式Shuffle
在深度學習 機器學習中,我們經常會使用到乙個叫shuffle函式,我一般叫打亂函式,也有人叫洗牌函式,就是聽著高階點,它可以幫助我們打亂資料集,那麼在go中我們如何實現乙個呢?大家可以直接使用我寫的乙個工具庫 lodago,有點lodash的味道。對於打亂函式有很多演算法實現,由於我的場景並不需要實...