问题描述
如何原生实现生成随机字符串?
解决方法
方法一
Math.random().toString(36).slice(-8)
Math.random() // 生成随机数字, eg: 0.123456
.toString(36) // 转化成36进制 : "0.4fzyo82mvyr"
.slice(-8);// 截取最后八位 : "yo82mvyr"
36进制包含的字符为 0-9,a-z。
10进制包含的字符为为 0-9。
16进制包含的字符为 0-9,a-f。
缺点:
- 只能生成有 0-9、a-z字符组成的字符串
- 由于 Math.random()生成的18位小数,可能无法填充36位,最后几个字符串,只能在指定的几个字符中选择。导致随机性降低。
- 某些情况下会返回空值。例如,当随机数为 0, 0.5, 0.25, 0.125…时,返回为空值。
方法二
可指定字符集
function randomString(length, chars) {
var result = '';
for (var i = length; i > 0; --i) result += chars[Math.floor(Math.random() * chars.length)];
return result;
}
var rString = randomString(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ');
方法三
使用randomString,e表示长度,默认32位
function randomString(e) {
e = e || 32;
var t = "ABCDEFGHJKMNPQRSTWXYZabcdefhijkmnprstwxyz2345678",
a = t.length,
n = "";
for (i = 0; i < e; i++) n += t.charAt(Math.floor(Math.random() * a));
return n
}
alert(randomString(6));
方法四
对定义的数组字符集进行随机选取
var str = ['0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'];
function generateMixed(n) {
var res = "";
for(var i = 0; i < n ; i ++) {
var id = Math.ceil(Math.random()*35);
res += str[id];
}
return res;
}
alert(generateMixed(6));
方法五
在NodeJS中,使用 crypto生成
'use strict';
const crypto = require('crypto');
module.exports = len => {
// isFinite 判断是否为有限数值
if (!Number.isFinite(len)) {
throw new TypeError('Expected a finite number');
}
return crypto.randomBytes(Math.ceil(len / 2)).toString('hex').slice(0, len);
};
crypto.randomBytes(size[, callback])
:
作用:生成加密强伪随机数据. size参数是指示要生成的字节数的数值。
crypto.randomBytes
生成的是字节数。
因此,若 size为1(1个字节8位),则最后转化成16进制(4位)时,为2个字符。
总结
第一种方法代码精简,可以快速获取随机字符串。但是存在较多缺点,不建议在生产中使用。对于对字符集有特定要求的场景,可以使用第二种方法。
生成随机数
// 本例子代表生成100000-999999的随机数
function GetRandomNum(Min,Max){
var Range = Max - Min;
var Rand = Math.random();
return(Min + Math.round(Rand * Range));
}
var num = GetRandomNum(10000,999999);
alert(num);