Skip to content

Commit d44c3d9

Browse files
Update utils.ts
Hi @j0pgrm, re #81 Your `if` statement is there to cover the possbility that your PRNG will generate the number 1. In general, PRNGs produce values from 0 to _less than_ 1, i.e. from the range 0 (inclusive) to 1 (exclusive). This is because when they generate an N-bit binary fraction, the highest value (all `1`s) will be just a tiny bit smaller than 1. Your `Math.floor` correctly rounds downward, so that `rand` will be in the range 0 (inclusive) to ENCODING_LEN *- 1* (inclusive). So the `if` will never be triggered. If, for some reason, you in future switch to a prng that somehow can generate a 1, for example because it has an idiosyncratic desire to cover a range of 0 (_exclusive_) to 1 (_inclusive_), then: * the chance of this is extremely small (1 in 2**N, not 1 in 2**8) * the PRNG will have lost the ability to generate 0 * your random character generator would have a micrscopically smaller chance of generating the first encoding character, and have a microscopic chance of trying to pick the non-existent character at #ENCODING_LEN. A neat solution for you is to simply wrap round that exactly-1 PRNG value back to 0, most conveniently A simple way to achieve this is to modulo the `rand` by ENCODING_LEN. Thank you for an excellent library.
1 parent 361eb27 commit d44c3d9

1 file changed

Lines changed: 7 additions & 5 deletions

File tree

source/utils.ts

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,11 +2,13 @@ import { ENCODING, ENCODING_LEN } from "./constants.js";
22
import { PRNG } from "./types.js";
33

44
export function randomChar(prng: PRNG): string {
5-
let rand = Math.floor(prng() * ENCODING_LEN);
6-
if (rand === ENCODING_LEN) {
7-
rand = ENCODING_LEN - 1;
8-
}
9-
return ENCODING.charAt(rand);
5+
6+
// Currently PRNGs generate fractions from 0 to _less than_ 1, so no "%" is necessary.
7+
// However, just in case a future PRNG can generate 1,
8+
// we are applying "% ENCODING LEN" to wrap back to the first character
9+
10+
const randomPosition = Math.floor(prng() * ENCODING_LEN) % ENCODING_LEN;
11+
return ENCODING.charAt(randPosition);
1012
}
1113

1214
export function replaceCharAt(str: string, index: number, char: string): string {

0 commit comments

Comments
 (0)