hasard

    1.6.1 • Public • Published

    Build Status

    codecov

    Installation

    npm install hasard
    

    Description

    Random variables and random nested objects manipulation in javascript

    Inspired by :

    Features:

    • Generate basic types randomly (string, number, boolean, integer)
    • Nested random object (array, object, matrix)
    • Use distribution to generate numbers (normal, uniform, truncated-normal) and integers (poisson, uniform)
    • Add reference + context to fix a random variable value in a local context
    • Easy-to-use common operators on random variable (add, substract, divide, multiply, round, ceil, floor)
    • Create custom operators
    • Change the Pseudorandom number generator
    • Stream API

    Simple Usage

    const h = require('hasard');
     
    const v = h.object({
        color: h.value(['white', 'yellow']), // randomly choose between 2 values
        size: h.integer(10, 20) // randomly choose an integer between 10 and 20
    });
     
    const values = v.run(3);
    console.log(values);
    // [{color: 'white', size: 12}, {color: 'yellow', size: 18}, {color: 'yellow', size: 17}]
     
    const value = v.runOnce();
    console.log(value);
    // {color: 'white', size: 13}

    Prng

    You can customize the Pseudorandom number generator which is Math.random by default.

    const n = h.value({choices: ['white', 'yellow'], prng: <custom prng>})

    Basic types

    h.value

    h.value(Array.<Hasard> | Hasard.<Array>)

    const v = h.value(['white', 'yellow']);

    h.value({choices: Array.<Hasard> | Hasard.<Array>, weights}) -> Hasard

    const v = h.value({
        choices: ['white', 'yellow'],
        weights: [0.75, 0.25]
    });

    h.boolean

    h.boolean({Hasard.<Number>} probability) -> Hasard.<Boolean>

    const v = h.boolean(0.2); // will be true 20% of the time

    h.boolean({prob: Hasard.<Number>}) -> Hasard.<Boolean>

    const v = h.boolean({prob: 0.3}); // will be true 30% of the time

    h.number

    h.number({Hasard.<Number>} start, {Hasard.<Number>} end) -> Hasard.<Number>

    const v = h.number(0, 1);

    h.number([{Hasard.<Number>} start, {Hasard.<Number>} end]) -> Hasard.<Number>

    const v = h.number([0, 1]);

    h.number({type: String, ...}) -> Hasard.<Number>

    Available distribution for numbers are

    • normal
    • uniform
    • truncated-normal

    Please Open an issue if you need another distribution

    const v = h.number({
        type: 'uniform',
        start: 0,
        end: 1
    });
    const v = h.number({
        type: 'normal',
        mean: -2,
        std: 3
    });

    h.integer

    h.integer({Hasard.<Integer>} start,{Hasard.<Integer>} end) -> Hasard.<Integer>

    const v = h.integer(0, 10);

    h.integer([{Hasard.<Integer>} start,{Hasard.<Integer>} end]) -> Hasard.<Integer>

    const v = h.integer([0, 10]);

    h.integer({type: String, ...}) -> Hasard.<Integer>

    For now, the only available distribution for integer is poisson, please Open an issue

    const v = h.integer({
        type: 'poisson',
        lambda: 3
    });

    h.string

    h.string({value: Hasard, size: Hasard.<integer>}) -> Hasard.<String>

    const v = h.string({
        value: h.value(["a", "b", "c", "d"]),
        size: h.integer([5, 10])
    });

    h.array

    h.array({value: Hasard, size: Hasard.<Integer>}) -> Hasard.<Array>

    const v = h.array({
        value: h.integer([0, 255]),
        size: h.integer([5, 10]),
    });

    h.array(Array.<Hasard>) -> Hasard.<Array>

    const v = h.array([
        h.integer([0, 255]),
        h.integer([0, 255]),
        h.integer([0, 255])
    ]);

    h.array({values: Array.<Hasard>, size: Hasard.<Integer>, randomOrder: Hasard.<Boolean>}) -> Hasard.<Array>

    // pick 5 digits in a randomOrder
    const v = h.array({
        values: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
        size: 5,
        randomOrder: true
    });

    h.object

    h.object(Object.<String, Hasard>) -> Hasard.<Object>

    const obj = h.object({
        color1 : h.value(['white', 'yellow']),
        color2 : h.value(['black', 'grey'])
    });

    h.object(Hasard.<Array.>, Hasard) -> Hasard.<Object>

    const phoneNumber = hasard.array({
        value: hasard.add(
            new hasard.Value(['+33', '+32', '+1']),
            new hasard.String({
                value: new hasard.Value(['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']),
                size: 9 // 9 digits in phone numbers
            })
        ),
        size : 5 // 5 keys
    });
     
    const fullName = hasard.add(
        new hasard.Value(['Mr ', '']),
        new hasard.Value(['Thomas ', 'Nicolas ', 'Julien ', 'Quentin ', 'Maxime ']),
        new hasard.Value(['DURAND', 'DUBOIS', 'LEFEBVRE', 'MOREAU', 'MOREL', 'FOURNIER'])
    );
     
    const randomPhoneDirectory = h.object(phoneNumber, fullName);
     
    randomPhoneDirectory.run(2) // run 2 times
    //
    // { 
    //   '+33236972292': 'M Julien FOURNIER',
    //   '+1833509762': 'Mr Quentin DURAND',
    //   '+33210149263': 'Mr Maxime MOREAU',
    //   '+1807872258': 'Mr Julien DURAND',
    //   '+32215961607': 'M Julien DUBOIS'
    // }
    // 
    // { 
    //   '+32067043361': 'Mr Nicolas MOREL',
    //   '+33898861064': 'Mr Thomas DURAND',
    //   '+33730685919': 'Mr Nicolas MOREL',
    //   '+33723780566': 'M Nicolas FOURNIER',
    //   '+33515400984': 'Mr Quentin DUBOIS'
    // }

    h.matrix

    h.matrix({value: Hasard, shape: Hasard.<Array.<Integer>>}) -> Hasard.<Matrix>

    create matrix with a specific shape

    const v = h.matrix({
        value: h.integer([0, 255]),
        shape: [128, 128, 3]
    });

    create random matrix with random values and random size

    const v = h.matrix({
        value: h.integer([0, 255]),
        shape: h.array({
            value: h.integer([5, 10]),
            size: h.integer([1, 4])
        })
    });

    h.reference

    h.reference(Hasard) -> Hasard

    A reference is generated only once per objet per run.

    Let's take an example of how it can be used

    const value = h.integer([0, 255]);
    const v = h.array([
        value,
        value,
        value
    ]);
     
    v.run(2);
    // all values are randomized independently
    // [[22, 128, 54], [250, 134, 12]]
     
    const ref = h.reference(h.Integer([0, 255]));
    const v = h.array([
        ref,
        ref,
        ref
    ]);
     
    v.run(2);
    // reference is reused inside the same run
    // [[72, 72, 72], [114, 114, 114]]

    h.reference({source: Hasard, context: Hasard.<String>}) -> Hasard

    When defined with a context, the reference is related to a context. You can define a context with any Hasard tool, by using {contextName: &lt;name of the context&gt;}

     
    // we will create a grey image in RGB so R = G = B
    const ref = h.reference({
        source: h.Integer([0, 255]),
        context: 'pixel'
    });
     
    // Here we need to use the form h.array({values, contextName})
    const pixel = h.array({
        values: [
            ref,
            ref,
            ref
        ],
        contextName: 'pixel'
    });
     
    const img = h.matrix({
        value: pixel,
        shape: [2,2]
    })
     
    v.run(2);
    // reference is reused inside the same pixel
    // [
    //   [[[12, 12, 12],[145, 145, 145]],[[251, 251, 251],[88, 88, 88]]], // first run,
    //   [[[212, 212, 212],[2, 2, 2]],[[78, 78, 78],[130, 130, 130]]] // second run,
    //]

    Helpers

    h.isHasard(Any) -> Boolean

    Check if the object is an instance of the hasard library

    const value = h.integer([0, 255]);
     
    h.isHasard(value); // true
    h.isHasard([0, 255]); // false

    h.fn(Function(Any, ...)) -> Function(Hasard.<Any>, ...)

    Example of use

    const refA = h.reference(h.number(0, 1));
    const refB = h.reference(h.number(0, 1));
     
    const addHasard = h.fn((a, b) =&gt; {
        return a + b;
    });
     
    const obj = h.object({
        a: refA,
        b: refB,
        sum: addHasard(refA, refB)
    });

    Shortcuts

    Hasard provides shortcuts for most common operations

    h.add(Hasard.<Number>, Hasard.<Number>, ...) -> Hasard.<Number>

    const refA = h.reference(h.number(0, 1));
    const refB = h.reference(h.number(0, 1));
     
    const obj = h.object({
        a: refA,
        b: refB,
        sum: h.add(refA, refB)
    });

    h.add(Hasard.<String>, Hasard.<String>, ...) -> Hasard.<String>

    const a = h.value(['M. ', 'Mme ']);
    const b = h.value(['DUPONT', 'DURANT']);
     
    h.add(a, b).run(2)
    // ['M. DUPONT', 'M. DURANT']

    h.substract(Hasard.<Number>, Hasard.<Number>) -> Hasard.<Number>

    const refA = h.reference(h.number(0, 1));
    const refB = h.reference(h.number(0, 1));
     
    const obj = h.object({
        a: refA,
        b: refB,
        diff: h.substract(refA, refB)
    });

    h.multiply(Hasard.<Number>, Hasard.<Number>) -> Hasard.<Number>

    const refA = h.reference(h.number(0, 1));
    const refB = h.reference(h.number(0, 1));
     
    const obj = h.object({
        a: refA,
        b: refB,
        mul: h.multiply(refA, refB)
    });

    h.divide(Hasard.<Number>, Hasard.<Number>) -> Hasard.<Number>

    const refA = h.reference(h.number(0, 1));
    const refB = h.reference(h.number(1, 2));
     
    const obj = h.object({
        a: refA,
        b: refB,
        ratio: h.divide(refA, refB)
    });

    h.if(Hasard.<Boolean>, Hasard, Hasard) -> Hasard

    const test = h.boolean(0.5);
    const poisson = h.reference(h.integer({type: 'poisson', lambda: '3'}));
     
    const signedPoisson = h.multiply(h.if(test, -1, 1), poisson)

    h.round(Hasard.<Number>) -> Hasard.<Integer>

    const int = h.round(h.number(0, 10));

    h.floor(Hasard.<Number>) -> Hasard.<Integer>

    const int = h.floor(h.number(0, 10));

    h.ceil(Hasard.<Number>) -> Hasard.<Integer>

    const int = h.ceil(h.number(0, 10));

    h.concat(Hasard.<Array>, Hasard.<Array>) -> Hasard.<Array>

    const int = h.concat([1,2], h.array({value: h.integer([0, 10]), size: 3}));

    h.getProperty(Hasard.<Number>, Hasard.<Object> | Hasard.<Array>) -> Hasard

    const int = h.getProperty(0, h.array({value: h.integer([0, 10]), size: 3}));

    Nested randomness

    Using set method, object properties can be set afterward

    Generate a random nested Object

    const randomValue = h.value();
     
    const randomInteger = h.integer({type: 'poisson', lambda: 4});
     
    const randomString = h.string({
        size: h.add(randomInteger, 5),
        value: h.value('abcdefghijklmnopkrstuvw'.split(''))
    });
     
    const randomNumber = h.number(0, 100);
     
    const randomKeys = h.array({
        size: randomInteger,
        value: randomString
    });
     
    const randomObject = h.object(
        randomKeys,
        randomValue
    );
     
    randomValue.set({
        choices: [
            randomString,
            randomObject,
            randomNumber,
            randomInteger
        ]
    });
     
    console.log(randomObject.run(1));

    Stream API

    const h = require('hasard');
     
    const v = h.object({
        color: h.value(['white', 'yellow']), // randomly choose between 2 values
        size: h.integer(10, 20) // randomly choose an integer between 10 and 20
    });
     
    const streamValue = v.stream(3);
     
    streamValue.on('data', d => {
        console.log(d);
    })

    Install

    npm i hasard

    DownloadsWeekly Downloads

    46

    Version

    1.6.1

    License

    MIT

    Unpacked Size

    229 kB

    Total Files

    31

    Last publish

    Collaborators

    • avatar