256

JavaScriptでランダムな英数字(大文字、小文字、数字)の文字列を生成して、おそらく一意の識別子として使用するための(理由の範囲内で)最短の方法は何ですか?

4

19 に答える 19

397

私はこれを本当に素晴らしくエレガントなソリューションとして見つけました:

Math.random().toString(36).slice(2)

この実装に関する注意:

  • これにより、浮動小数点の文字列化によって末尾のゼロが削除されるため、長さが 0 ~ 12 文字 (通常は 11 文字) の文字列が生成されます。
  • 大文字は生成せず、小文字と数字のみを生成します。
  • ランダム性は から得られるためMath.random()、出力は予測可能であり、必ずしも一意であるとは限りません。
  • 理想的な実装を想定しても、出力のエントロピーは最大で 52 ビットです。これは、約 70M 文字列が生成された後に重複が予想されることを意味します。
于 2012-09-19T20:40:12.513 に答える
336

特定の文字のみを許可する場合は、次のようにすることもできます。

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');

デモ用の jsfiddle を次に示します: http://jsfiddle.net/wSQBx/

別の方法として、使用する文字の種類を関数に伝える特別な文字列を使用することもできます。次のようにできます。

function randomString(length, chars) {
    var mask = '';
    if (chars.indexOf('a') > -1) mask += 'abcdefghijklmnopqrstuvwxyz';
    if (chars.indexOf('A') > -1) mask += 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
    if (chars.indexOf('#') > -1) mask += '0123456789';
    if (chars.indexOf('!') > -1) mask += '~`!@#$%^&*()_+-={}[]:";\'<>?,./|\\';
    var result = '';
    for (var i = length; i > 0; --i) result += mask[Math.floor(Math.random() * mask.length)];
    return result;
}

console.log(randomString(16, 'aA'));
console.log(randomString(32, '#aA'));
console.log(randomString(64, '#A!'));

フィドル: http://jsfiddle.net/wSQBx/2/

または、以下で説明するように base36 メソッドを使用するには、次のようにすることもできます。

function randomString(length) {
    return Math.round((Math.pow(36, length + 1) - Math.random() * Math.pow(36, length))).toString(36).slice(1);
}
于 2012-05-23T20:13:58.367 に答える
37

JAR.JAR.beans によって提案された回答の別のバリエーション

(Math.random()*1e32).toString(36)

乗数1e32を変更すると、ランダム文字列の長さを変更できます。

于 2015-06-18T20:49:18.747 に答える
37

更新: ランダムな 20 文字 (英数字の小文字) のワンライナー ソリューション:

Array.from(Array(20), () => Math.floor(Math.random() * 36).toString(36)).join('');

またはlodashで短くします:

_.times(20, () => _.random(35).toString(36)).join('');
于 2017-06-19T04:33:10.920 に答える
21

これはきれいです

Math.random().toString(36).substr(2, length)

Math.random().toString(36).substr(2, 5)
于 2016-07-04T16:58:22.353 に答える
8

32 文字の場合:

for(var c = ''; c.length < 32;) c += Math.random().toString(36).substr(2, 1)
于 2014-06-30T19:01:05.353 に答える
7

ロダッシュの使用:

function createRandomString(length) {
        var chars = "abcdefghijklmnopqrstufwxyzABCDEFGHIJKLMNOPQRSTUFWXYZ1234567890"
        var pwd = _.sampleSize(chars, length || 12)  // lodash v4: use _.sampleSize
        return pwd.join("")
    }
document.write(createRandomString(8))
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>

于 2016-04-26T07:54:09.617 に答える
6

ランダム文字:

String.fromCharCode(i); //where is an int

ランダム整数:

Math.floor(Math.random()*100);

すべてをまとめる:

function randomNum(hi){
    return Math.floor(Math.random()*hi);
} 
function randomChar(){
    return String.fromCharCode(randomNum(100));
}
function randomString(length){
   var str = "";
   for(var i = 0; i < length; ++i){
        str += randomChar();
   }
   return str;
}
var RandomString = randomString(32); //32 length string

フィドル: http://jsfiddle.net/maniator/QZ9J2/

于 2012-05-23T19:56:26.963 に答える
2

この質問を見たとき、いつ UUID を生成しなければならないかを考えました。ここでスタックオーバーフローで見つけたと確信しているので、コードの功績を認めることはできません。文字列にダッシュが必要ない場合は、ダッシュを削除します。関数は次のとおりです。

function generateUUID() {
    var d = new Date().getTime();
    var uuid = 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g,function(c) {
        var r = (d + Math.random()*16)%16 | 0;
        d = Math.floor(d/16);
        return (c=='x' ? r : (r&0x7|0x8)).toString(16);
    });
    return uuid.toUpperCase();
}

フィドル: http://jsfiddle.net/nlviands/fNPvf/11227/

于 2015-01-19T18:26:58.397 に答える
1

この関数は、任意の長さのランダムな文字列を提供する必要があります。

function randString(length) {
    var l = length > 25 ? 25 : length;
    var str = Math.random().toString(36).substr(2, l);
    if(str.length >= length){
        return str;
    }
    return str.concat(this.randString(length - str.length));
}

私は成功した次のテストでそれをテストしました。

function test(){
    for(var x = 0; x < 300000; x++){
        if(randString(x).length != x){
            throw new Error('invalid result for len ' + x);
        }
    }
}

25 を選択した理由は、実際には返される文字列の長さが 25 であるためですMath.random().toString(36).substr(2, 25)。この数は必要に応じて変更できます。

この関数は再帰的であるため、非常に大きな値で関数を呼び出すと、Maximum call stack size exceeded. 私のテストでは、300,000 文字の長さの文字列を取得できました。

この関数は、文字列を 2 番目のパラメーターとして関数に送信することにより、末尾再帰に変換できます。JS が Tail 呼び出しの最適化を使用しているかどうかはわかりません

于 2016-08-10T13:03:14.777 に答える
1

素晴らしくシンプルで、特定の文字数に制限されていません:

let len = 20, str = "";
while(str.length < len) str += Math.random().toString(36).substr(2);
str = str.substr(0, len);
于 2017-05-16T14:52:38.360 に答える
-2

MD5 ライブラリを使用: https://github.com/blueimp/JavaScript-MD5

最短の方法:

md5(Math.random())

サイズを 5 に制限する場合:

md5(Math.random()).substr(0, 5)

于 2016-06-16T22:01:39.617 に答える