本文对比了JavaScript中生成不重复随机数的三种实现方案。方案1利用slice截取数组,内存开销大;方案2通过置空已取元素避免重复,效率提升但尾部性能下降;方案3采用数组打乱后遍历,在1-3000数据量下耗时仅234毫秒,综合性能最优。
方案1:数组截取法及其性能瓶颈
不重复的随机数方案1:1531 毫秒 一般的思路是先创建一个1-3000的数组,每一次取出一个,然后让这个数组减少一个, 取一个,减少一个,这样就可以做到永不重复了。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>随机不重复_www.jb51.net</title> </head> <body> 本站 </body> </html> [[t1]]
不重复的随机数方案2:297毫秒
方案2:置空法优化与尾部性能问题
然而,方案1使用了slice方法来重新生成数组,这会导致大量的内存分配和CPU计算资源消耗,整体效率较低。为此进行改良:从原始数组中取出一个数值后,不删除该元素,而是将其位置赋值为null。在后续取数时,若遇到null则跳过,直到找到非null值为止。经测试,这种方法能显著提高执行效率。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>随机不重复_本站_www.jb51.net</title> </head> <body> 本站 </body> </html> [[t3]]
不重复的随机数方案3:234毫秒
方案3:数组打乱法的高效实现
转换思路,如果将原始数组origin进行随机打乱(洗牌算法),然后按顺序依次输出其中的元素,
同样可以实现随机且不重复的效果,并且效率更高。
这是因为方案2在运行后期,原始数组中为null的元素比例越来越高,导致查找有效数字时需要遍历的次数大幅增加,运算耗时随之增加。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>随机不重复_www.jb51.net</title> </head> <body> 本站 </body> </html> [[t7]]