JavaScript에서 랜덤 문자열/문자 생성
세트에서 무작위로 뽑은 5글자 스트링을 원합니다.[a-zA-Z0-9]
.
JavaScript를 사용하여 이를 수행하는 가장 좋은 방법은 무엇입니까?
이게 너한테 효과가 있을 것 같아.
function makeid(length) {
var result = '';
var characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
var charactersLength = characters.length;
for ( var i = 0; i < length; i++ ) {
result += characters.charAt(Math.floor(Math.random() *
charactersLength));
}
return result;
}
console.log(makeid(5));
//Can change 7 to 2 for longer results.
let r = (Math.random() + 1).toString(36).substring(7);
console.log("random", r);
주의: 위의 알고리즘에는 다음과 같은 약점이 있습니다.
- 부동 소수점 문자열화 시 후행 0이 제거되므로 0에서 6자 사이의 문자가 생성됩니다.
- 부동소수점 번호를 문자열화하는 데 사용되는 알고리즘에 따라 크게 달라지는데, 이는 매우 복잡합니다.('부동소수점 번호를 정확하게 인쇄하는 방법' 참조).
Math.random()
는, 실장에 따라 예측 가능한(「외관상」이지만, 실제로는 랜덤이 아닌) 출력을 생성할 수 있습니다.일의성 또는 예측 불가능성을 보증할 필요가 있는 경우 결과 문자열은 적합하지 않습니다.- 6개의 랜덤한 예측 불가능한 문자가 균일하게 생성되었다고 해도 생일 패러독스로 인해 약 50,000개의 문자열만 생성하면 중복이 발생할 수 있습니다. (490rt(36^6) = 46656)
옵션 1
서버측에서 이 작업을 수행할 수 있다면 암호 모듈을 사용하십시오.
var crypto = require("crypto");
var id = crypto.randomBytes(20).toString('hex');
// "bb5dc8842ca31d4603d6aa11448d1654"
결과 문자열은 생성되는 랜덤바이트의 2배 길이입니다.16진수로 인코딩된 각 바이트는 2자, 20바이트는 16진수 40자입니다.
옵션 2
이 클라이언트측을 실행할 필요가 있는 경우는, UUID 모듈을 사용해 주세요.
var uuid = require("uuid");
var id = uuid.v4();
// "110ec58a-a0f2-4ac4-8393-c866d813b8d1"
옵션 3
이 클라이언트측을 실행할 필요가 있고 오래된 브라우저를 지원할 필요가 없다면 의존하지 않고 실행할 수 있습니다.
// dec2hex :: Integer -> String
// i.e. 0-255 -> '00'-'ff'
function dec2hex (dec) {
return dec.toString(16).padStart(2, "0")
}
// generateId :: Integer -> String
function generateId (len) {
var arr = new Uint8Array((len || 40) / 2)
window.crypto.getRandomValues(arr)
return Array.from(arr, dec2hex).join('')
}
console.log(generateId())
// "82defcf324571e70b0521d79cce2bf3fffccd69"
console.log(generateId(20))
// "c1a050a4cd1556948d41"
상세한 것에 대하여는, 다음을 참조해 주세요.
crypto.getRandomValues()
method를 사용하면 암호로 강력한 랜덤 값을 얻을 수 있습니다.파라미터로 지정된 배열은 랜덤 번호(암호화 의미에서의 랜덤)로 채워집니다.
다음은 콘솔의 예를 제시하겠습니다.
> var arr = new Uint8Array(4) # make array of 4 bytes (values 0-255)
> arr
Uint8Array(4) [ 0, 0, 0, 0 ]
> window.crypto
Crypto { subtle: SubtleCrypto }
> window.crypto.getRandomValues()
TypeError: Crypto.getRandomValues requires at least 1 argument, but only 0 were passed
> window.crypto.getRandomValues(arr)
Uint8Array(4) [ 235, 229, 94, 228 ]
IE11 의 서포트에 대해서는, 다음을 참조해 주세요.
(window.crypto || window.msCrypto).getRandomValues(arr)
브라우저의 적용범위에 대해서는 https://caniuse.com/ #syslog=getrandomvalues를 참조하십시오.
짧고 간단하며 신뢰성 높은 제품
여기서 발견된 상위 등급의 답변이 아닌 정확히 5개의 랜덤 문자를 반환합니다.
Math.random().toString(36).slice(2, 7);
Double Tap의 우수한 답변에 대한 개선점을 소개합니다.원본에는 다음 두 가지 단점이 있습니다.
첫째, 다른 사용자가 언급했듯이 짧은 문자열이나 빈 문자열(랜덤 번호가 0인 경우)이 생성될 가능성이 적기 때문에 응용 프로그램이 중단될 수 있습니다.해결책은 다음과 같습니다.
(Math.random().toString(36)+'00000000000000000').slice(2, N+2)
둘째, 원본과 위의 솔루션 모두 문자열 크기 N을 16자로 제한합니다.다음은 임의의 N에 대해 크기N의 문자열을 반환합니다(단, N > 16을 사용해도 랜덤성이 증가하거나 충돌 확률이 감소하는 것은 아닙니다).
Array(N+1).join((Math.random().toString(36)+'00000000000000000').slice(2, 18)).slice(0, N)
설명:
- [0,1] 범위의 임의의 숫자, 즉 0(포함)과 1(포함) 사이에서 선택합니다.
- 숫자 0-9 및 a-z를 사용하여 숫자를 base-36 문자열로 변환합니다.
- 0이 붙은 패드(첫 번째 문제 해결).
- 선행하는 '0' 접두사와 추가 패딩 0을 잘라냅니다.
- 빈 문자열을 딜리미터로 사용되는 짧은 랜덤 문자열과 결합함으로써 N자 이상의 문자를 포함할 수 있을 정도로 문자열을 반복합니다.
- 문자열에서 정확히 N자를 잘라냅니다.
상세 내용:
- 이 솔루션에서는 대문자는 사용하지 않지만 거의 모든 경우(말장난 의도 없음)에는 문제가 없습니다.
- 원본 답변의 최대 문자열 길이는 N = 16으로 Chrome으로 측정됩니다.Firefox에서는 N = 11입니다.그러나 설명한 바와 같이 두 번째 솔루션은 요청된 문자열 길이를 지원하는 것이지 랜덤성을 추가하는 것이 아니기 때문에 큰 차이는 없습니다.
- 반환되는 모든 문자열은 적어도 Math.random()에 의해 반환된 결과가 균등하게 분포되어 있는 한 반환될 확률은 동일합니다(이는 어떤 경우에도 암호 강도의 랜덤성이 아닙니다).
- 크기가 N인 문자열이 모두 반환되는 것은 아닙니다.두 번째 솔루션에서는 (작은 문자열이 단순히 복제되기 때문에) 이는 명백하지만, 원래 답변에서는 base-36으로 변환될 때 마지막 몇 비트가 원래 랜덤비트의 일부가 아닐 수 있기 때문에 이 또한 사실입니다.특히 Math.random().toString(36)의 결과를 보면 마지막 문자가 균등하게 분포되어 있지 않다는 것을 알 수 있습니다.다시 말하지만, 거의 모든 경우 문제가 되지 않지만, 짧은 문자열(예: N=1)이 영향을 받지 않도록 랜덤 문자열의 끝이 아니라 처음부터 마지막 문자열을 잘라냅니다.
업데이트:
여기 제가 생각해낸 기능성 스타일의 원라이너가 몇 개 더 있습니다.위의 솔루션과 다른 점은 다음과 같습니다.
- 이들은 명시적인 임의의 알파벳을 사용합니다(더 일반적이며 대소문자를 모두 요구한 원래 질문에 적합합니다).
- 길이 N의 모든 문자열은 반환될 확률이 동일합니다(즉, 문자열에는 반복이 없습니다).
- 이들은 toString(36) 트릭이 아닌 맵 함수를 기반으로 하기 때문에 보다 간단하고 이해하기 쉽습니다.
자, 당신이 선택한 알파벳은
var s = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
이 두 가지는 서로 동등하기 때문에 사용자가 보다 직관적인 것을 선택할 수 있습니다.
Array(N).join().split(',').map(function() { return s.charAt(Math.floor(Math.random() * s.length)); }).join('');
그리고.
Array.apply(null, Array(N)).map(function() { return s.charAt(Math.floor(Math.random() * s.length)); }).join('');
편집:
Qubyte와 Martijn de Milliano가 후자와 비슷한 솔루션을 생각해 낸 것 같습니다(kudos!).그것은 왠지 놓치고 있었습니다.언뜻 보기에는 그렇게 짧아 보이지 않기 때문에, 누군가가 정말로 원라이너를 원할 경우를 대비해서, 어쨌든 여기에 두겠습니다:-)
또한 모든 솔루션에서 '새로운 어레이'를 '어레이'로 교체하여 몇 바이트를 더 절약합니다.
가 보다 짧기 때문에 가장 콤팩트한 솔루션. 문자열 끝에서 빼면 함수에 의해 생성되는 부동소수점 기호를 피할 수 있습니다.
Math.random().toString(36).slice(-5);
또는 심지어
(+new Date).toString(36).slice(-5);
업데이트: 다음 방법을 사용하여 접근법 하나 추가:
btoa(Math.random()).slice(0, 5);
btoa(+new Date).slice(-7, -2);
btoa(+new Date).substr(-7, 5);
// Using Math.random and Base 36:
console.log(Math.random().toString(36).slice(-5));
// Using new Date and Base 36:
console.log((+new Date).toString(36).slice(-5));
// Using Math.random and Base 64 (btoa):
console.log(btoa(Math.random()).slice(0, 5));
// Using new Date and Base 64 (btoa):
console.log(btoa(+new Date).slice(-7, -2));
console.log(btoa(+new Date).substr(-7, 5));
es6 스프레드 연산자를 사용하는 최신 버전:
[...Array(30)].map(() => Math.random().toString(36)[2]).join('')
30
수치로 할 수 .36
numeric.toString()에 전달할 수 있는 최대 기수입니다.이것은 모든 숫자와 a-z 소문자를 의미합니다.2
에서 세 하기 위해 합니다.는 '3번째 인덱스는 다음과"0.mfbiohx64i"
, , , , , , , , , , , , , , , , , , , , , , , , , , , , , , 뒤에 어떤 을 취할 수.0.
이런 게 효과가 있을 거야
function randomString(len, charSet) {
charSet = charSet || 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
var randomString = '';
for (var i = 0; i < len; i++) {
var randomPoz = Math.floor(Math.random() * charSet.length);
randomString += charSet.substring(randomPoz,randomPoz+1);
}
return randomString;
}
디폴트 문자 집합 [a-zA-Z0-9]로 콜하거나, 독자적인 문자를 송신합니다.
var randomValue = randomString(5);
var randomValue = randomString(5, 'PICKCHARSFROMTHISSET');
function randomstring(L) {
var s = '';
var randomchar = function() {
var n = Math.floor(Math.random() * 62);
if (n < 10) return n; //1-10
if (n < 36) return String.fromCharCode(n + 55); //A-Z
return String.fromCharCode(n + 61); //a-z
}
while (s.length < L) s += randomchar();
return s;
}
console.log(randomstring(5));
랜덤 문자열 생성기(영숫자| 영숫자| 숫자)
/**
* Pseudo-random string generator
* http://stackoverflow.com/a/27872144/383904
* Default: return a random alpha-numeric string
*
* @param {Integer} len Desired length
* @param {String} an Optional (alphanumeric), "a" (alpha), "n" (numeric)
* @return {String}
*/
function randomString(len, an) {
an = an && an.toLowerCase();
var str = "",
i = 0,
min = an == "a" ? 10 : 0,
max = an == "n" ? 10 : 62;
for (; i++ < len;) {
var r = Math.random() * (max - min) + min << 0;
str += String.fromCharCode(r += r > 9 ? r < 36 ? 55 : 61 : 48);
}
return str;
}
console.log(randomString(10)); // i.e: "4Z8iNQag9v"
console.log(randomString(10, "a")); // i.e: "aUkZuHNcWw"
console.log(randomString(10, "n")); // i.e: "9055739230"
위에서는 필요한 A/N, A, N 출력에 대한 추가 체크를 사용하고 있습니다만, 를 에센셜(영숫자만 해당)로 나누어 보다 잘 이해하도록 하겠습니다.
- 인수를 받아들이는 함수를 만듭니다(임의 문자열 결과의 원하는 길이).
- 빈 을 만듭니다.
var str = "";
를 - 루프 내부에 0 ~ 61의 인덱스 번호를 만듭니다(0.9+A).Z+a..z = 62)
- 조정/수정하기 위한 조건부 로직을 만듭니다(0이므로).61) 권리를 되찾기 위해 그것을 몇 개씩 증가시킨다(아래 예 참조).
CharCode
을 사용하다 - 에서는 " "에 되어 있습니다.
str
aString.fromCharCode( incremented rand )
ASCII 문자 테이블 범위를 그려보겠습니다.
_____0....9______A..........Z______a..........z___________ Character
| 10 | | 26 | | 26 | Tot = 62 characters
48....57 65..........90 97..........122 CharCode ranges
Math.floor( Math.random * 62 )
~의 0..61
( 한한 (것 )
random을 수정하여 올바른 charCode 범위를 가져옵니다.
| rand | charCode | (0..61)rand += fix = charCode ranges |
------+----------+----------+--------------------------------+-----------------+
0..9 | 0..9 | 48..57 | rand += 48 = 48..57 |
A..Z | 10..35 | 65..90 | rand += 55 /* 90-35 = 55 */ = 65..90 |
a..z | 36..61 | 97..122 | rand += 61 /* 122-61 = 61 */ = 97..122 |
위의 표의 조건부 동작 로직:
rand += rand>9 ? ( rand<36 ? 55 : 61 ) : 48 ;
// rand += true ? ( true ? 55 else 61 ) else 48 ;
위 설명에서 얻은 영숫자 스니펫은 다음과 같습니다.
function randomString(len) {
var str = ""; // String result
for (var i = 0; i < len; i++) { // Loop `len` times
var rand = Math.floor(Math.random() * 62); // random: 0..61
var charCode = rand += rand > 9 ? (rand < 36 ? 55 : 61) : 48; // Get correct charCode
str += String.fromCharCode(charCode); // add Character to str
}
return str; // After all loops are done, return the concatenated string
}
console.log(randomString(10)); // i.e: "7GL9F0ne6t"
또는 다음과 같이 하십시오.
const randomString = (n, r='') => {
while (n--) r += String.fromCharCode((r=Math.random()*62|0, r+=r>9?(r<36?55:61):48));
return r;
};
console.log(randomString(10))
요구 사항 [a-zA-Z0-9] 및 길이=5를 충족하려면
브라우저의 경우:
btoa(Math.random().toString()).substr(10, 5);
노드의 경우JS:
Buffer.from(Math.random().toString()).toString("base64").substr(10, 5);
소문자, 대문자 및 숫자가 표시됩니다.
(타자기호환)
가장 간단한 방법은 다음과 같습니다.
(new Date%9e6).toString(36)
그러면 현재 시간에 따라 5자로 구성된 임의의 문자열이 생성됩니다. 예시는 '보다 낫다' 입니다.4mtxj
★★★★★★★★★★★★★★★★★」4mv90
★★★★★★★★★★★★★★★★★」4mwp1
이 문제의 문제는 같은 1초에 2회 호출하면 같은 문자열이 생성된다는 것입니다.
보다 안전한 방법은 다음과 같습니다.
(0|Math.random()*9e6).toString(36)
이렇게 하면 4~5자로 이루어진 임의의 문자열이 생성됩니다.항상 다른 문자열이 생성됩니다. 예시는 '먹다'와 같은 입니다.30jzm
★★★★★★★★★★★★★★★★★」1r591
★★★★★★★★★★★★★★★★★」4su1a
두 가지 방법으로 첫 번째 부품은 난수를 생성합니다..toString(36)
는 그합니다.part cast는 base36(영숫자)로 표현합니다.
을 사용하다new Array(5)
길이를 설정합니다.
<<고객명>>님 포함0-9a-z
new Array(5).join().replace(/(.|$)/g, function(){return ((Math.random()*36)|0).toString(36);})
<<고객명>>님 포함0-9a-zA-Z
new Array(5).join().replace(/(.|$)/g, function(){return ((Math.random()*36)|0).toString(36)[Math.random()<.5?"toString":"toUpperCase"]();});
(ES6용)0-9a-z
)
Array(5).fill().map(()=>((Math.random()*36)|0).toString(36)).join('')
모두가 이미 잘 알고 있다는 것을 알고 있지만, 가능한 한 가벼운 방법으로 이것을 시도해 보고 싶다고 생각하고 있습니다(CPU가 아닌 코드상의 라이트 온).
function rand(length, current) {
current = current ? current : '';
return length ? rand(--length, "0123456789ABCDEFGHIJKLMNOPQRSTUVWXTZabcdefghiklmnopqrstuvwxyz".charAt(Math.floor(Math.random() * 60)) + current) : current;
}
console.log(rand(5));
머리를 싸매는 데는 시간이 좀 걸리지만 자바스크립트의 구문이 얼마나 멋진지 알 수 있다고 생각합니다.
이것을 하는 최선의 방법은 없다.원하는 대로 할 수 있습니다.요건에 맞는 결과만 있으면 됩니다.예를 들면, 다양한 예를 작성했습니다만, 모두 같은 최종 결과를 얻을 수 있습니다.
이 페이지의 다른 대부분의 답변은 대문자의 요건을 무시합니다.
여기 가장 빠르고 가장 읽기 쉬운 솔루션이 있습니다.기본적으로는 조금 더 빠르다는 점만 제외하면 허용되는 솔루션과 동일하게 동작합니다.
function readableRandomStringMaker(length) {
for (var s=''; s.length < length; s += 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'.charAt(Math.random()*62|0));
return s;
}
console.log(readableRandomStringMaker(length));
// e3cbN
읽기 어려운 컴팩트하고 재귀적인 버전을 다음에 나타냅니다.
const compactRandomStringMaker = (length) => length-- && "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62|0) + (compactRandomStringMaker(length)||"");
console.log(compactRandomStringMaker(5));
// DVudj
보다 콤팩트한 원라이너:
Array(5).fill().map(()=>"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62)).join("")
// 12oEZ
상기의 변형:
" ".replaceAll(" ",()=>"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62))
가장 콤팩트한 한 줄이지만 비효율적이고 읽을 수 없습니다. 길이가 l:가 될 때까지 임의의 문자를 추가하고 잘못된 문자를 제거합니다.
((l,f=(p='')=>p.length<l?f(p+String.fromCharCode(Math.random()*123).replace(/[^a-z0-9]/i,'')):p)=>f())(5)
암호화로 보호된 버전입니다.이 버전은 콤팩트함을 위해 엔트로피를 낭비하고 있으며 생성된 문자열이 너무 짧기 때문에 어떤 경우에도 낭비입니다.
[...crypto.getRandomValues(new Uint8Array(999))].map((c)=>String.fromCharCode(c).replace(/[^a-z0-9]/i,'')).join("").substr(0,5)
// 8fzPq
또는 length-argument를 사용하지 않으면 더 짧아집니다.
((f=(p='')=>p.length<5?f(p+String.fromCharCode(Math.random()*123).replace(/[^a-z0-9]/i,'')):p)=>f())()
// EV6c9
그런 다음 이름 없는 재귀 화살표 함수를 사용하여 조금 더 까다롭습니다.
((l,s=((l)=>l--&&"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62|0)+(s(l)||""))) => s(l))(5);
// qzal4
이것은 "매직" 변수이며, 사용자가 접근할 때마다 임의의 문자를 제공합니다.
const c = new class { [Symbol.toPrimitive]() { return "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62|0) } };
console.log(c+c+c+c+c);
// AgMnz
위의 간단한 변형:
const c=()=>"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".charAt(Math.random()*62|0);
c()+c()+c()+c()+c();
// 6Qadw
랜덤 영숫자 「」를 합니다.Base-62
★★★★★★★★★★★★★★★★★★:
function generateUID(length)
{
return window.btoa(Array.from(window.crypto.getRandomValues(new Uint8Array(length * 2))).map((b) => String.fromCharCode(b)).join("")).replace(/[+/]/g, "").substring(0, length);
}
console.log(generateUID(22)); // "yFg3Upv2cE9cKOXd7hHwWp"
console.log(generateUID(5)); // "YQGzP"
메모리를 한 번에 할당하는 원라이너(편리한 포맷은 아니지만)에 관심이 있는 경우(단, 작은 문자열에 대해서는 그다지 중요하지 않음) 방법은 다음과 같습니다.
Array.apply(0, Array(5)).map(function() {
return (function(charset){
return charset.charAt(Math.floor(Math.random() * charset.length))
}('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'));
}).join('')
할 수 요.5
원하는 문자열 길이만큼만 사용할 수 있습니다.@Ariya님 덕분입니다.이 투고에서는 Hidayat에 대한 해결책에 대해 설명합니다.map
하지 Array(5)
.
Lodash 또는 언더스코어를 사용하는 경우 다음과 같이 간단합니다.
var randomVal = _.sample('ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789', 5).join('');
const c = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'
const s = [...Array(5)].map(_ => c[~~(Math.random()*c.length)]).join('')
제가 만든 방법은 다음과 같습니다.
대문자와 소문자를 모두 포함하는 문자열이 생성됩니다.
또, 영숫자 문자열을 작성하는 기능도 추가했습니다.
「 」:
http://jsfiddle.net/greatbigmassive/vhsxs/ (알파만)
http://jsfiddle.net/greatbigmassive/PJwg8/ (영어)
function randString(x){
var s = "";
while(s.length<x&&x>0){
var r = Math.random();
s+= String.fromCharCode(Math.floor(r*26) + (r>0.5?97:65));
}
return s;
}
7월 7월
이것은 같은 기능을 하지만 모든 문자를 포함하여 더 말이 됩니다.
var s = "";
while(s.length<x&&x>0){
v = Math.random()<0.5?32:0;
s += String.fromCharCode(Math.round(Math.random()*((122-v)-(97-v))+(97-v)));
}
위의 @Andrew 답변 개선:
Array.from({ length : 1 }, () => Math.random().toString(36)[2]).join('');
Base 36 의 난수 변환은 일관성이 없기 때문에, 1 개의 Indice 를 선택하면 수정됩니다.문자열의 길이를 원하는 대로 변경할 수 있습니다.
언더스코어를 사용한다고 가정하면, 단 두 줄만으로 우아하게 랜덤 문자열을 생성할 수 있습니다.
var possible = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
var random = _.sample(possible, 5).join('');
라이너 1개:
Array(15).fill(null).map(() => Math.random().toString(36).substr(2)).join('')
// Outputs: 0h61cbpw96y83qtnunwme5lxk1i70a6o5r5lckfcyh1dl9fffydcfxddd69ada9tu9jvqdx864xj1ul3wtfztmh2oz2vs3mv6ej0fe58ho1cftkjcuyl2lfkmxlwua83ibotxqc4guyuvrvtf60naob26t6swzpil
고속으로 개선된 알고리즘균일성을 보장하지 않습니다(주석 참조).
function getRandomId(length) {
if (!length) {
return '';
}
const possible =
'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
let array;
if ('Uint8Array' in self && 'crypto' in self && length <= 65536) {
array = new Uint8Array(length);
self.crypto.getRandomValues(array);
} else {
array = new Array(length);
for (let i = 0; i < length; i++) {
array[i] = Math.floor(Math.random() * 62);
}
}
let result = '';
for (let i = 0; i < length; i++) {
result += possible.charAt(array[i] % 62);
}
return result;
}
function randomString (strLength, charSet) {
var result = [];
strLength = strLength || 5;
charSet = charSet || 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
while (strLength--) { // (note, fixed typo)
result.push(charSet.charAt(Math.floor(Math.random() * charSet.length)));
}
return result.join('');
}
이것은 더할 나위 없이 깨끗하다.http://jsperf.com/ay-random-string도 빠릅니다.
이 작고 작은 트릭은 어때?
var possible = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
var stringLength = 5;
function pickRandom() {
return possible[Math.floor(Math.random() * possible.length)];
}
var randomString = Array.apply(null, Array(stringLength)).map(pickRandom).join('');
★★★★★★★★★★★★★★★★가 필요합니다.Array.apply
빈 배열을 정의되지 않은 배열로 속입니다.
ES2015를 코딩하는 경우 어레이 구축이 조금 더 간단합니다.
var randomString = Array.from({ length: stringLength }, pickRandom).join('');
예를 들어 랜덤 DNA 시퀀스를 원하는 경우 항목 배열을 루프하여 문자열 변수에 항목을 재귀적으로 추가할 수 있습니다.
function randomDNA(len) {
len = len || 100
var nuc = new Array("A", "T", "C", "G")
var i = 0
var n = 0
s = ''
while (i <= len - 1) {
n = Math.floor(Math.random() * 4)
s += nuc[n]
i++
}
return s
}
console.log(randomDNA(5));
대소문자를 구분하지 않는 영숫자:
function randStr(len) {
let s = '';
while (s.length < len) s += Math.random().toString(36).substr(2, len - s.length);
return s;
}
// usage
console.log(randStr(50));
이 함수의 장점은 다양한 길이의 랜덤 문자열을 얻을 수 있으며 문자열의 길이를 보장할 수 있다는 것입니다.
대소문자를 구분하는 모든 문자:
function randStr(len) {
let s = '';
while (len--) s += String.fromCodePoint(Math.floor(Math.random() * (126 - 33) + 33));
return s;
}
// usage
console.log(randStr(50));
커스텀 문자
function randStr(len, chars='abc123') {
let s = '';
while (len--) s += chars[Math.floor(Math.random() * chars.length)];
return s;
}
// usage
console.log(randStr(50));
console.log(randStr(50, 'abc'));
console.log(randStr(50, 'aab')); // more a than b
랜덤 문자열이 필요합니다(어느 언어로든) 질문에 대한 응답의 문제는 거의 모든 솔루션이 문자열 길이의 기본 사양을 사용한다는 것입니다.질문 자체는 랜덤 문자열이 필요한 이유를 거의 밝히지 않지만, 예를 들어 8개의 랜덤 문자열이 필요한 경우는 거의 없습니다.반드시 필요한 것은, 예를 들면, 특정의 목적을 위해서 식별자로 사용하는, 몇개의 일의 문자열입니다.
엄밀하게 일의적인 문자열을 취득하는 방법에는 결정론적으로(랜덤이 아님) 및 저장/비교(부담스러운)의 2가지가 있습니다.어떻게 해야 하죠?우리는 유령을 포기한다.우리는 대신 확률론적 독특함을 택한다.즉, 당사 문자열이 고유하지 않을 위험이 있다는 것을 인정합니다.여기서 충돌 확률과 엔트로피를 이해하는 것이 도움이 됩니다.
따라서 반복의 위험이 적은 몇 개의 문자열이 필요하다는 점에서 불변의 필요성을 다시 설명하겠습니다.예를 들어, 500만 개의 ID를 생성할 수 있다고 가정해 보겠습니다.각 새 문자열을 저장 및 비교하고 싶지 않고 랜덤 문자열로 만들고 싶기 때문에 반복의 위험을 감수해야 합니다.예를 들어, 반복 확률이 1조분의 1 미만이라고 가정해 보겠습니다.그럼 끈 길이가 얼마나 필요하죠?음, 그 질문은 사용된 문자에 따라 다르기 때문에 덜 구체화되어 있습니다.하지만 더 중요한 건, 그건 잘못된 거야.필요한 것은 문자열의 길이가 아니라 엔트로피를 지정하는 것입니다.엔트로피는 일부 문자열의 반복 확률과 직접 관련될 수 있습니다.문자열 길이는 사용할 수 없습니다.
여기서 엔트로피 스트링과 같은 라이브러리가 도움이 됩니다.500만 문자열에서 반복 확률이 1조분의 1 미만인 랜덤 ID를 생성하려면entropy-string
:
import {Random, Entropy} from 'entropy-string'
const random = new Random()
const bits = Entropy.bits(5e6, 1e12)
const string = random.string(bits)
"44hTNGHJNHGRHH9"
entropy-string
는 디폴트로 32글자의 문자 세트를 사용합니다.미리 정의된 다른 문자 집합이 있으며 고유한 문자도 지정할 수 있습니다.예를 들어 위와 같은 엔트로피를 가지지만 16진수 문자를 사용하여 ID를 생성하는 경우:
import {Random, Entropy, charSet16} from './entropy-string'
const random = new Random(charSet16)
const bits = Entropy.bits(5e6, 1e12)
const string = random.string(bits)
"27b33372ade513715481f"
사용된 문자 집합의 총 문자 수의 차이로 인한 문자열 길이 차이점에 유의하십시오.지정된 수의 잠재적 문자열에서 반복될 위험은 동일합니다.문자열 길이는 그렇지 않습니다.그리고 무엇보다도 반복의 위험과 잠재적인 문자열 수가 명확합니다.더 이상 문자열 길이로 추측할 필요가 없습니다.
암호 강화
요건을 충족하는 암호 스트링 스트링을 취득하는 경우(이를 사용하지만 유효하지 않은 응답을 제공하는 응답이 표시됩니다)
let pass = n=> [...crypto.getRandomValues(new Uint8Array(n))]
.map((x,i)=>(i=x/255*61|0,String.fromCharCode(i+(i>9?i>35?61:55:48)))).join``
let pass = n=> [...crypto.getRandomValues(new Uint8Array(n))]
.map((x,i)=>(i=x/255*61|0,String.fromCharCode(i+(i>9?i>35?61:55:48)))).join``
console.log(pass(5));
업데이트: Zibri 댓글 덕분에 임의 긴 암호를 얻기 위해 코드를 업데이트합니다.
언급URL : https://stackoverflow.com/questions/1349404/generate-random-string-characters-in-javascript
'programing' 카테고리의 다른 글
mariaDB, 여러 테이블에서 삭제가 정말 안전합니까? (0) | 2022.10.12 |
---|---|
php에서 실행 시간 초과를 늘리는 방법 (0) | 2022.10.12 |
고정폭 정수형(예: uint8_t)을 사용하지 않는 이유가 있습니까? (0) | 2022.10.12 |
Python에서 날짜를 datetime으로 변환 (0) | 2022.10.12 |
아나콘다 대 미니콘다 (0) | 2022.10.12 |