Skip to main content
`Ctrl`+`K`

# Source code for SALib.sample.latin

    from typing import Optional, Union

    import numpy as np

    from . import common_args
    from ..util import read_param_file, scale_samples, compute_groups_matrix, handle_seed

    def sample(problem, N, seed: Optional[Union[int, np.random.Generator, None]] = None):
        """Generate model inputs using Latin hypercube sampling (LHS).

        Returns a NumPy matrix containing the model inputs generated by Latin
        hypercube sampling.  The resulting matrix contains N rows and D columns,
        where D is the number of parameters.

        Parameters
        ----------
        problem : dict
            The problem definition
        N : int
            The number of samples to generate
        seed : {None, int, `numpy.random.Generator`}, optional
            If `seed` is None the `numpy.random.Generator` generator is used.
            If `seed` is an int, a new ``Generator`` instance is used,
            seeded with `seed`.
            If `seed` is already a ``Generator`` instance then that instance is
            used. Default is None.

        References
        ----------
        1. McKay, M.D., Beckman, R.J., Conover, W.J., 1979.
               A comparison of three methods for selecting values of input
               variables in the analysis of output from a computer code.
               Technometrics 21, 239-245.
               https://doi.org/10.2307/1268522

        2. Iman, R.L., Helton, J.C., Campbell, J.E., 1981.
               An Approach to Sensitivity Analysis of Computer Models:
               Part I—Introduction, Input Variable Selection and
               Preliminary Variable Assessment.
               Journal of Quality Technology 13, 174-183.
               https://doi.org/10.1080/00224065.1981.11978748

        """
        rng = handle_seed(seed)

        num_samples = N

        groups = problem.get("groups")
        if groups:
            num_groups = len(set(groups))
            G, group_names = compute_groups_matrix(groups)
        else:
            num_groups = problem["num_vars"]

        result = np.empty([num_samples, problem["num_vars"]])
        temp = np.empty([num_samples])
        d = 1.0 / num_samples

        temp = np.array(
            [
                rng.uniform(low=sample * d, high=(sample + 1) * d, size=num_groups)
                for sample in range(num_samples)
            ]
        )

        for group in range(num_groups):
            rng.shuffle(temp[:, group])

            for sample in range(num_samples):
                if groups:
                    grouped_variables = np.where(G[:, group] == 1)
                    result[sample, grouped_variables[0]] = temp[sample, group]
                else:
                    result[sample, group] = temp[sample, group]

        result = scale_samples(result, problem)

        return result

    # No additional CLI options
    cli_parse = None

    def cli_action(args):
        """Run sampling method

        Parameters
        ----------
        args : argparse namespace
        """
        problem = read_param_file(args.paramfile)
        param_values = sample(problem, args.samples, seed=args.seed)
        np.savetxt(
            args.output,
            param_values,
            delimiter=args.delimiter,
            fmt="%." + str(args.precision) + "e",
        )

    if __name__ == "__main__":
        common_args.run_cli(cli_parse, cli_action)