首页 > 编程知识 正文

js洗牌算法,洗牌算法原理

时间:2023-05-05 13:40:48 阅读:119274 作者:4588

1 .问题描述洗牌算法是一个常见的随机问题,它可以抽象为m以内所有自然数的随机序列。

常见问题解答说明:

1 .将自然数1 ~ 100随机插入尺寸为100的排列中,无重复要素

2 .洗牌2. 1 ~ 52张扑克牌

什么是好的洗牌算法:

洗牌后,如果能够确保每个数出现在所有位置的概率相等,则该算法在满足要求的前提下尽量降低时间和空间复杂度。

2 .算法实现第一个算法:

随机抽取一张卡,检查是否抽取了这张卡,如果抽取了,重新抽取,重复这个知道找到了没有抽取的卡的过程,知道所有的卡都被抽取了。

该算法适用于大脑的直观思维。 该算法有两种形式。

1 .每次随机抽取后,取出抽取的卡片,此时剩下的卡片为(N-1 )。 该算法避免了重复抽取,但每次抽取一张卡后,都有删除操作,需要从原始数组中删除随机选择的卡() (可通过Hashtable实现)。

2 .每次随机抽取后,标记符合抽取要求的卡片,但不删除; 与1相比,省略了删除操作,但外部存储标志可能会增加空间,从而每次都可以提取以前抽的卡

这种方法时间/空间复杂度差。

第二种算法:

每次随机取出两张卡进行更换,更换一定次数后结束:

voidshuffle(int*Array,int len ) { const int suff_time=len; for(intidx=0; i suff_time; I ) intI=rand(%Len; intj=rand(%len; int temp=array[i]; array[i]=array[j]; array[j]=temp; }

这是常见的洗牌算法,但是如何确定合适的更换次数?

假设更换m这个的话,某个卡永远不会被更换的概率是(n-2 )/n )-2 )/n,) (n-2 )/n=(n-2 )/n ) ^m; 期待该概率比触摸的值小,求出m的解。假设概率小于1/1000,则相对于n=52,m约为176,实际上远远大于数组的长度。

第三个算法:

FisherYates shuffle算法

该算法每次随机选择一个数,并与数组中的最后(或第一个)元素进行交换。 如果随机选择的是最后/第一个元素,则表示没有进行交换)。 然后缩小选定数组的范围,删除最后一个元素,也就是以前随机提取的数量。 重复上述步骤,直到剩下的数组大小为1,即只有一个元素。

voidshuffle(int*Array,int len ) int len; int j=0; int temp==0; if(I==0) {返回; (while(-I ) { j=rand ) % ) I1 ); temp=array[i]; array[i]=array[j]; array[j]=temp; }

该算法的数学证明见具体论文或博文;

该算法的复杂度为o(n ),各元素的随机概率相等。

版权声明:该文观点仅代表作者本人。处理文章:请发送邮件至 三1五14八八95#扣扣.com 举报,一经查实,本站将立刻删除。