Skip to content

Instantly share code, notes, and snippets.

@blixt
Last active November 5, 2021 13:42
Show Gist options
  • Select an option

  • Save blixt/9abfafdd0ada0f4f6f26 to your computer and use it in GitHub Desktop.

Select an option

Save blixt/9abfafdd0ada0f4f6f26 to your computer and use it in GitHub Desktop.

Revisions

  1. blixt revised this gist Aug 2, 2014. 2 changed files with 24 additions and 11 deletions.
    16 changes: 10 additions & 6 deletions TestingRNGs.md
    Original file line number Diff line number Diff line change
    @@ -44,18 +44,22 @@ Communicating with Dieharder
    ----------------------------

    Dieharder can take a file as an input, so we'll use a simple Node.js script for generating a dump of random numbers. See
    `randout.js` below for a template file that implements the simple Park-Miller PRNG.
    `randout.js` below for a template file that implements an integer version of the built-in RNG as well as the very simple
    Park-Miller PRNG.

    Make the file executable (`chmod +x randout.js`) then execute it and put its output into a file:

    ```
    ./randout.js > numbers.txt
    ./randout.js > math.random.txt
    ```

    **Note:** By default this will create 10,000,000 random numbers. That takes time and space, but is necessary for an accurate
    test.

    And now you can test it with Dieharder:

    ```
    dieharder -g 202 -f numbers.txt -a
    dieharder -g 202 -f math.random.txt -a
    ```

    You can read more about the `dieharder` tool on the [Dieharder homepage][dieharder], but this will run all tests on that file. **Note:** It will take some time!
    @@ -64,11 +68,11 @@ You can read more about the `dieharder` tool on the [Dieharder homepage][diehard
    Testing more PRNGs
    ------------------

    You can now add more constructors for other PRNGs in `randout.js`. They just need a `random` method which returns a 32-bit
    integer. To change which constructor is used, call the script with the `--prng` argument:
    You can now add more constructors for other PRNGs in `randout.js`. They just need a `next` method which returns an integer.
    To change which constructor is used, call the script with the `--prng` argument:

    ```
    ./randout.js --prng MersenneTwister > numbers.txt
    ./randout.js --prng ParkMiller > park-miller.txt
    ```


    19 changes: 14 additions & 5 deletions randout.js
    Original file line number Diff line number Diff line change
    @@ -2,18 +2,27 @@

    var argv = require('minimist')(process.argv.slice(2));

    // 32-bit integer conversion of the built-in RNG.
    function JavaScript() {}
    JavaScript.prototype.next = function () {
    return Math.random() * 4294967296 >>> 0;
    };
    JavaScript.NUM_BITS = 32;

    // Park-Miller.
    function ParkMiller(seed) {
    this._seed = seed % 2147483647;
    if (this._seed <= 0) this._seed += 2147483646;
    }
    ParkMiller.NUM_BITS = 31;

    ParkMiller.prototype.next = function () {
    return this._seed = this._seed * 16807 % 2147483647;
    };

    var SEED = argv.seed || 1,
    COUNT = argv.count || 100000,
    PRNG = argv.prng || 'ParkMiller';
    var SEED = argv.seed || 12345,
    COUNT = argv.count || 10000000,
    PRNG = argv.prng || 'JavaScript';

    var RandomClass = eval(PRNG);
    if (!RandomClass) {
    @@ -24,11 +33,11 @@ process.stdout.write('# ' + PRNG + '\n');
    process.stdout.write('# seed: ' + SEED + '\n');
    process.stdout.write('type: d\n');
    process.stdout.write('count: ' + COUNT + '\n');
    process.stdout.write('numbit: 32\n');
    process.stdout.write('numbit: ' + (RandomClass.NUM_BITS || 32) + '\n');

    var r = new RandomClass(SEED);
    for (var i = 0; i < COUNT; i++) {
    var num = r.next().toString();
    num = ' '.slice(0, 10 - num.length) + num;
    process.stdout.write(num + '\n');
    }
    }
  2. blixt revised this gist Aug 2, 2014. 1 changed file with 3 additions and 3 deletions.
    6 changes: 3 additions & 3 deletions TestingRNGs.md
    Original file line number Diff line number Diff line change
    @@ -1,5 +1,5 @@
    Testing random number generators with DieHarder
    ===============================================
    Testing RNGs with Dieharder
    ===========================

    This guide is specifically for pseudo-random number generators (PRNGs) written in JavaScript, and tested in Mac OS X.

    @@ -21,7 +21,7 @@ You can now use Homebrew to install Node.js ([site][nodejs]):
    brew install node
    ```

    **DieHarder**
    **Dieharder**
    Homebrew also lets you install Dieharder, the tool that tests RNGs ([site][dieharder]):

    ```
  3. blixt created this gist Aug 2, 2014.
    77 changes: 77 additions & 0 deletions TestingRNGs.md
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,77 @@
    Testing random number generators with DieHarder
    ===============================================

    This guide is specifically for pseudo-random number generators (PRNGs) written in JavaScript, and tested in Mac OS X.


    Prerequisites
    -------------

    **Homebrew**
    Run this in the Terminal to install Homebrew ([site][homebrew]):

    ```
    ruby -e "$(curl -fsSL https://raw.github.com/Homebrew/homebrew/go/install)"
    ```

    **Node.js**
    You can now use Homebrew to install Node.js ([site][nodejs]):

    ```
    brew install node
    ```

    **DieHarder**
    Homebrew also lets you install Dieharder, the tool that tests RNGs ([site][dieharder]):

    ```
    brew install dieharder
    ```

    **A directory for your testing**
    Create a directory which you'll use for testing PRNGs. This is where we'll put scripts and data.

    **The `minimist` package**
    A very useful package for parsing arguments which I use for the script below. Go into the testing directory and install it
    with NPM:

    ```
    npm install minimist
    ```


    Communicating with Dieharder
    ----------------------------

    Dieharder can take a file as an input, so we'll use a simple Node.js script for generating a dump of random numbers. See
    `randout.js` below for a template file that implements the simple Park-Miller PRNG.

    Make the file executable (`chmod +x randout.js`) then execute it and put its output into a file:

    ```
    ./randout.js > numbers.txt
    ```

    And now you can test it with Dieharder:

    ```
    dieharder -g 202 -f numbers.txt -a
    ```

    You can read more about the `dieharder` tool on the [Dieharder homepage][dieharder], but this will run all tests on that file. **Note:** It will take some time!


    Testing more PRNGs
    ------------------

    You can now add more constructors for other PRNGs in `randout.js`. They just need a `random` method which returns a 32-bit
    integer. To change which constructor is used, call the script with the `--prng` argument:

    ```
    ./randout.js --prng MersenneTwister > numbers.txt
    ```


    [homebrew]: http://brew.sh/
    [nodejs]: http://nodejs.org/
    [dieharder]: http://www.phy.duke.edu/~rgb/General/dieharder.php
    34 changes: 34 additions & 0 deletions randout.js
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,34 @@
    #!/usr/bin/env node

    var argv = require('minimist')(process.argv.slice(2));

    function ParkMiller(seed) {
    this._seed = seed % 2147483647;
    if (this._seed <= 0) this._seed += 2147483646;
    }

    ParkMiller.prototype.next = function () {
    return this._seed = this._seed * 16807 % 2147483647;
    };

    var SEED = argv.seed || 1,
    COUNT = argv.count || 100000,
    PRNG = argv.prng || 'ParkMiller';

    var RandomClass = eval(PRNG);
    if (!RandomClass) {
    throw new Error('Invalid PRNG ' + PRNG);
    }

    process.stdout.write('# ' + PRNG + '\n');
    process.stdout.write('# seed: ' + SEED + '\n');
    process.stdout.write('type: d\n');
    process.stdout.write('count: ' + COUNT + '\n');
    process.stdout.write('numbit: 32\n');

    var r = new RandomClass(SEED);
    for (var i = 0; i < COUNT; i++) {
    var num = r.next().toString();
    num = ' '.slice(0, 10 - num.length) + num;
    process.stdout.write(num + '\n');
    }