Ejemplo n.º 1
0
        /// <summary>
        /// Samples a two-domain function randomly with the provided distribution.
        /// </summary>
        /// <param name="function">The real-domain function to sample.</param>
        /// <param name="distribution">Random distribution of the real domain sample points.</param>
        /// <param name="sampleCount">The number of samples to generate.</param>
        /// <typeparam name="T">The value type of the function to sample.</typeparam>
        /// <returns>The generated sample vector.</returns>
        /// <exception cref="ArgumentNullException" />
        /// <exception cref="ArgumentOutOfRangeException" />
        public static T[] Random <T>(
            Func <double, double, T> function,
            IContinuousDistribution distribution,
            int sampleCount)
        {
            if (ReferenceEquals(function, null))
            {
                throw new ArgumentNullException("function");
            }

            if (ReferenceEquals(distribution, null))
            {
                throw new ArgumentNullException("distribution");
            }

            if (sampleCount < 0)
            {
                throw new ArgumentOutOfRangeException("sampleCount");
            }

            var samples = new T[sampleCount];

            for (int i = 0; i < samples.Length; i++)
            {
                samples[i] = function(distribution.Sample(), distribution.Sample());
            }

            return(samples);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Generate samples by sampling a function at sample pairs from a probability distribution.
        /// </summary>
        public static T[] RandomMap2 <T>(int length, IContinuousDistribution distribution, Func <double, double, T> map)
        {
            var data = new T[length];

            for (int i = 0; i < data.Length; i++)
            {
                data[i] = map(distribution.Sample(), distribution.Sample());
            }
            return(data);
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Samples a two-domain function randomly with the provided distribution.
        /// </summary>
        /// <param name="function">The real-domain function to sample.</param>
        /// <param name="distribution">Random distribution of the real domain sample points.</param>
        /// <param name="sampleCount">The number of samples to generate.</param>
        /// <typeparam name="T">The value type of the function to sample.</typeparam>
        /// <returns>The generated sample vector.</returns>
        /// <exception cref="ArgumentNullException" />
        /// <exception cref="ArgumentOutOfRangeException" />
        public static T[] Random <T>(Func <double, double, T> function, IContinuousDistribution distribution, int sampleCount)
        {
            function.ShouldNotBeNull("function");
            distribution.ShouldNotBeNull("distribution");
            sampleCount.ShouldBePositiveOrZero("sampleCount");

            return
                (Enumerable
                 .Range(0, sampleCount)
                 .AsParallel()
                 .AsOrdered()
                 .Select(i => function(distribution.Sample(), distribution.Sample()))
                 .ToArray());
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Generates a vector with random elements
        /// </summary>
        /// <param name="length">Number of elements in the vector.</param>
        /// <param name="randomDistribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// A vector with n-random elements distributed according
        /// to the specified random distribution.
        /// </returns>
        /// <exception cref="ArgumentException">If the n vector is non-positive.</exception>
        public override Vector <Complex> Random(int length, IContinuousDistribution randomDistribution)
        {
            if (length < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "length");
            }

            var vector = CreateVector(length);

            for (var index = 0; index < length; index++)
            {
                vector.At(index, new Complex(randomDistribution.Sample(), randomDistribution.Sample()));
            }

            return(vector);
        }
Ejemplo n.º 5
0
 public static IEnumerable <double> LatinHyperCubeSample(this IContinuousDistribution ContinuousDistribution, int divisions)
 {
     for (int i = 0; i < divisions; i++)
     {
         yield return(ContinuousDistribution.Sample());
     }
 }
Ejemplo n.º 6
0
        public static List<PatternClass> Create2DimTeachingVectors(double p1, double p2, IContinuousDistribution generatorFirstFeature1, IContinuousDistribution generatorFirstFeature2, IContinuousDistribution generatorSecondFeature1, IContinuousDistribution generatorSecondFeature2, int nrOfTeachingVectors)
        {
            List<PatternClass> createdTeachingVectors = new List<PatternClass>();
             if (probabilityGenerator == null)
             {
                 probabilityGenerator = new ContinuousUniform(0, 1);
                 probabilityGenerator.RandomSource = new Random(DateTime.Now.Millisecond + 10);
             }

             for (int i = 0; i < nrOfTeachingVectors; i++)
             {
                 double value = 0;
                 double value1 = 0;
                 int classNumber = CreateClass(p1, p2);

                 if (classNumber == 1)
                 {
                     value = generatorFirstFeature1.Sample();
                     value1 = generatorSecondFeature1.Sample();
                 }
                 else if (classNumber == 2)
                 {
                     value = generatorFirstFeature2.Sample();
                     value1 = generatorSecondFeature2.Sample();
                 }

                 createdTeachingVectors.Add(new PatternClass(new FeatureVector(value,value1), classNumber));
             }

             return createdTeachingVectors;
        }
Ejemplo n.º 7
0
        /// <summary>
        /// Create a new child genome from a given parent genome.
        /// </summary>
        /// <param name="parent">The parent genome.</param>
        /// <returns>A new child genome.</returns>
        public NeatGenome <T> CreateChildGenome(NeatGenome <T> parent)
        {
            Debug.Assert(_metaNeatGenome == parent.MetaNeatGenome, "Parent genome has unexpected MetaNeatGenome.");

            // Attempt to find a new connection that we can add to the genome.
            DirectedConnection directedConn;

            if (!TryGetConnection(parent, out directedConn, out int insertIdx))
            {   // Failed to find a new connection.
                return(null);
            }

            // Determine the connection weight.
            // 50% of the time use weights very close to zero.
            // Note. this recreates the strategy used in SharpNEAT 2.x.
            // ENHANCEMENT: Reconsider the distribution of new weights and if there are better approaches (distributions) we could use.
            T weight = _rng.NextBool() ? _weightDistB.Sample() : _weightDistA.Sample();

            // Create a new connection gene array that consists of the parent connection genes plus the new gene
            // inserted at the correct (sorted) position.
            var parentConnArr   = parent.ConnectionGenes._connArr;
            var parentWeightArr = parent.ConnectionGenes._weightArr;
            int parentLen       = parentConnArr.Length;

            // Create the child genome's ConnectionGenes object.
            int childLen  = parentLen + 1;
            var connGenes = new ConnectionGenes <T>(childLen);
            var connArr   = connGenes._connArr;
            var weightArr = connGenes._weightArr;

            // Copy genes up to insertIdx.
            Array.Copy(parentConnArr, connArr, insertIdx);
            Array.Copy(parentWeightArr, weightArr, insertIdx);

            // Copy the new genome into its insertion point.
            connArr[insertIdx] = new DirectedConnection(
                directedConn.SourceId,
                directedConn.TargetId);

            weightArr[insertIdx] = weight;

            // Copy remaining genes (if any).
            Array.Copy(parentConnArr, insertIdx, connArr, insertIdx + 1, parentLen - insertIdx);
            Array.Copy(parentWeightArr, insertIdx, weightArr, insertIdx + 1, parentLen - insertIdx);

            // Create and return a new genome.
            // Notes.
            // The set of hidden node IDs remains unchanged from the parent, therefore we are able to re-use parent.HiddenNodeIdArray.
            // However, the presence of a new connection invalidates parent.NodeIndexByIdMap for use in the new genome, because the allocated
            // node indexes are dependent on node depth in the acyclic graph, which in turn can be modified by the presence of a new connection.
            return(_genomeBuilder.Create(
                       _genomeIdSeq.Next(),
                       _generationSeq.Peek,
                       connGenes,
                       parent.HiddenNodeIdArray));
        }
Ejemplo n.º 8
0
 /// <summary>
 /// Populates a matrix with random elements.
 /// </summary>
 /// <param name="matrix">The matrix to populate.</param>
 /// <param name="distribution">Continuous Random Distribution to generate elements from.</param>
 protected override void DoRandom(Matrix <Complex32> matrix, IContinuousDistribution distribution)
 {
     for (var i = 0; i < matrix.RowCount; i++)
     {
         for (var j = 0; j < matrix.ColumnCount; j++)
         {
             matrix.At(i, j, Convert.ToSingle(distribution.Sample()));
         }
     }
 }
Ejemplo n.º 9
0
 /// <summary>
 /// Populates a matrix with random elements.
 /// </summary>
 /// <param name="matrix">The matrix to populate.</param>
 /// <param name="distribution">Continuous Random Distribution to generate elements from.</param>
 protected override void DoRandom(Matrix <double> matrix, IContinuousDistribution distribution)
 {
     for (var i = 0; i < matrix.RowCount; i++)
     {
         for (var j = 0; j < matrix.ColumnCount; j++)
         {
             matrix.At(i, j, distribution.Sample());
         }
     }
 }
        public void Invoke(double[] weightArr)
        {
            // Select a subset of connection genes to mutate.
            int[] selectedIdxArr = _selectionStrategy.SelectSubset(weightArr.Length);

            // Loop over the connection genes to be mutated, and mutate them.
            for (int i = 0; i < selectedIdxArr.Length; i++)
            {
                weightArr[selectedIdxArr[i]] += _dist.Sample();
            }
        }
Ejemplo n.º 11
0
        public static List<PatternClass> Create2dimSampleObject(IContinuousDistribution generator, IContinuousDistribution generator1, int count, int classNumber)
        {
            List<PatternClass> sampleObjects = new List<PatternClass>();

                         probabilityGenerator = new ContinuousUniform(0, 1);
             probabilityGenerator.RandomSource = new Random(DateTime.Now.Millisecond + 10);

            for (int i = 0; i < count; i++)
            {
                sampleObjects.Add(new PatternClass(new FeatureVector(generator.Sample(), generator1.Sample()), classNumber));
            }
            return sampleObjects;
        }
 /// <summary>
 /// Populates a matrix with random elements.
 /// </summary>
 /// <param name="matrix">The matrix to populate.</param>
 /// <param name="distribution">Continuous Random Distribution to generate elements from.</param>
 protected override void DoRandom(Matrix <Complex32> matrix, IContinuousDistribution distribution)
 {
     CommonParallel.For(
         0,
         matrix.RowCount,
         i =>
     {
         for (var j = 0; j < matrix.ColumnCount; j++)
         {
             matrix.At(i, j, Convert.ToSingle(distribution.Sample()));
         }
     });
 }
        /// <summary>
        /// Create a new child genome from a given parent genome.
        /// </summary>
        /// <param name="parent">The parent genome.</param>
        /// <returns>A new child genome.</returns>
        public NeatGenome <T> CreateChildGenome(NeatGenome <T> parent)
        {
            // Attempt to find a new connection that we can add to the genome.
            if (!TryGetConnection(parent, out DirectedConnection directedConn, out int insertIdx))
            {   // Failed to find a new connection.
                return(null);
            }

            // Determine the connection weight.
            // 50% of the time use weights very close to zero.
            // Note. this recreates the strategy used in SharpNEAT 2.x.
            // TODO: Reconsider the distribution of new weights and if there are better approaches (distributions) we could use.
            T weight = _rng.NextBool() ? _weightDistB.Sample() : _weightDistA.Sample();

            // Create a new connection gene array that consists of the parent connection genes plus the new gene
            // inserted at the correct (sorted) position.
            var parentConnArr   = parent.ConnectionGenes._connArr;
            var parentWeightArr = parent.ConnectionGenes._weightArr;
            int parentLen       = parentConnArr.Length;

            // Create the child genome's ConnectionGenes object.
            int childLen  = parentLen + 1;
            var connGenes = new ConnectionGenes <T>(childLen);
            var connArr   = connGenes._connArr;
            var weightArr = connGenes._weightArr;

            // Copy genes up to insertIdx.
            Array.Copy(parentConnArr, connArr, insertIdx);
            Array.Copy(parentWeightArr, weightArr, insertIdx);

            // Copy the new genome into its insertion point.
            connArr[insertIdx] = new DirectedConnection(
                directedConn.SourceId,
                directedConn.TargetId);

            weightArr[insertIdx] = weight;

            // Copy remaining genes (if any).
            Array.Copy(parentConnArr, insertIdx, connArr, insertIdx + 1, parentLen - insertIdx);
            Array.Copy(parentWeightArr, insertIdx, weightArr, insertIdx + 1, parentLen - insertIdx);

            // Create and return a new genome.
            // Note. The set of hidden node IDs remains unchanged from the parent, therefore we are able to re-use
            // both parent.HiddenNodeIdArray and NodeIndexByIdMap.
            return(_genomeBuilder.Create(
                       _genomeIdSeq.Next(),
                       _generationSeq.Peek,
                       connGenes,
                       parent.HiddenNodeIdArray,
                       parent.NodeIndexByIdMap));
        }
        /// <summary>
        /// Generates a vector with random elements
        /// </summary>
        /// <param name="length">Number of elements in the vector.</param>
        /// <param name="randomDistribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// A vector with n-random elements distributed according
        /// to the specified random distribution.
        /// </returns>
        /// <exception cref="ArgumentNullException">If the n vector is non positive<see langword="null" />.</exception>
        public override Vector <float> Random(int length, IContinuousDistribution randomDistribution)
        {
            if (length < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "length");
            }

            var v = CreateVector(length);

            for (var index = 0; index < Count; index++)
            {
                v[index] = Convert.ToSingle(randomDistribution.Sample());
            }

            return(v);
        }
Ejemplo n.º 15
0
        /// <summary>
        /// Generates a vector with random elements
        /// </summary>
        /// <param name="length">Number of elements in the vector.</param>
        /// <param name="randomDistribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// A vector with n-random elements distributed according
        /// to the specified random distribution.
        /// </returns>
        /// <exception cref="ArgumentNullException">If the n vector is non positive<see langword="null" />.</exception>
        public override Vector <Complex32> Random(int length, IContinuousDistribution randomDistribution)
        {
            if (length < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "length");
            }

            var v = (DenseVector)CreateVector(length);

            for (var index = 0; index < v.Data.Length; index++)
            {
                v.Data[index] = new Complex32((float)randomDistribution.Sample(), (float)randomDistribution.Sample());
            }

            return(v);
        }
Ejemplo n.º 16
0
        //static VectorBuilder<double> vBuilder;


        //public static Particle[] Generate2D(int numberOfParticles, IDistribution distributionx, IDistribution distributiony, IDistribution distributionv, IDistribution distributiono)
        //{

        //    return Enumerable.Range(0, numberOfParticles).Select(_ =>
        //    new Particle
        //        (
        //          distributionx.Sample(), distributiony.Sample(), distributionv.Sample(), distributiono.Sample() % 2.0 * System.Math.PI, weight: 1d
        //        )

        //    ).ToArray();

        //}


        public static List <Particle> BuildSwarm(int numberOfParticles,
                                                 IContinuousDistribution xdistribution, IContinuousDistribution ydistribution,
                                                 IContinuousDistribution vdistribution = null, IContinuousDistribution odistribution = null)
        {
            return(Enumerable.Range(0, numberOfParticles).Select(_ =>
            {
                var x = xdistribution.Sample();
                var y = ydistribution.Sample();
                var v = vdistribution?.Sample();
                var o = odistribution?.Sample();

                return new Particle(x, y, 1d / numberOfParticles)
                {
                    Velocity = v ?? 0, Orientation = o ?? 0
                };
            }).ToList());
        }
Ejemplo n.º 17
0
 /// <summary>
 /// Create a new dense vector with values sampled from the provided random distribution.
 /// </summary>
 public static DenseVector CreateRandom(int length, IContinuousDistribution distribution)
 {
     return new DenseVector(DenseVectorStorage<double>.OfInit(length,
         i => distribution.Sample()));
 }
 /// <summary>
 /// Create a new dense matrix with values sampled from the provided random distribution.
 /// </summary>
 public static DenseMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     return(new DenseMatrix(DenseColumnMajorMatrixStorage <Complex> .OfInit(rows, columns,
                                                                            (i, j) => new Complex(distribution.Sample(), distribution.Sample()))));
 }
Ejemplo n.º 19
0
 /// <summary>
 /// Create a new dense vector with values sampled from the provided random distribution.
 /// </summary>
 public static DenseVector CreateRandom(int length, IContinuousDistribution distribution)
 {
     return new DenseVector(DenseVectorStorage<Complex32>.OfInit(length,
         i => new Complex32((float)distribution.Sample(), (float)distribution.Sample())));
 }
        /// <summary>
        /// Generates a vector with random elements
        /// </summary>
        /// <param name="length">Number of elements in the vector.</param>
        /// <param name="randomDistribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// A vector with n-random elements distributed according
        /// to the specified random distribution.
        /// </returns>
        /// <exception cref="ArgumentNullException">If the length vector is non poisitive<see langword="null" />.</exception> 
        public override Vector Random(int length, IContinuousDistribution randomDistribution)
        {
            if (length < 0)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "length");
            }

            var v = (SparseVector)this.CreateVector(length);
            for (var index = 0; index < v.Count; index++)
            {
                v[index] = randomDistribution.Sample();
            }

            return v;
        }
Ejemplo n.º 21
0
 /// <summary>
 /// Create a new dense vector with values sampled from the provided random distribution.
 /// </summary>
 public static DenseVector CreateRandom(int size, IContinuousDistribution distribution)
 {
     var storage = new DenseVectorStorage<Complex>(size);
     for (var i = 0; i < storage.Data.Length; i++)
     {
         storage.Data[i] = new Complex(distribution.Sample(), distribution.Sample());
     }
     return new DenseVector(storage);
 }
Ejemplo n.º 22
0
 /// <summary>
 /// Create a new dense matrix with values sampled from the provided random distribution.
 /// </summary>
 public static DenseMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     return new DenseMatrix(DenseColumnMajorMatrixStorage<float>.OfInit(rows, columns, (i, j) => (float) distribution.Sample()));
 }
Ejemplo n.º 23
0
 /// <summary>
 /// Computes and returns the next sample.
 /// </summary>
 public double ReadNextSample()
 {
     return(_distribution.Sample());
 }
Ejemplo n.º 24
0
 /// <summary>
 /// Create a new dense matrix with values sampled from the provided random distribution.
 /// </summary>
 public static DenseMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     var storage = new DenseColumnMajorMatrixStorage<Complex>(rows, columns);
     for (var i = 0; i < storage.Data.Length; i++)
     {
         storage.Data[i] = new Complex(distribution.Sample(), distribution.Sample());
     }
     return new DenseMatrix(storage);
 }
Ejemplo n.º 25
0
 float _GetBias()
 {
     return(_zeroBias ? 0f : Convert.ToSingle(_distribution.Sample()));
 }
Ejemplo n.º 26
0
        /// <summary>
        /// Generates a vector with random elements
        /// </summary>
        /// <param name="length">Number of elements in the vector.</param>
        /// <param name="randomDistribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// A vector with n-random elements distributed according
        /// to the specified random distribution.
        /// </returns>
        /// <exception cref="ArgumentNullException">If the n vector is non positive<see langword="null" />.</exception> 
        public override Vector<Complex32> Random(int length, IContinuousDistribution randomDistribution)
        {
            if (length < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "length");
            }

            var v = (DenseVector)CreateVector(length);
            for (var index = 0; index < v.Data.Length; index++)
            {
                v.Data[index] = new Complex32((float)randomDistribution.Sample(), (float)randomDistribution.Sample());
            }

            return v;
        }
Ejemplo n.º 27
0
        /// <summary>
        /// Generates matrix with random elements.
        /// </summary>
        /// <param name="numberOfRows">Number of rows.</param>
        /// <param name="numberOfColumns">Number of columns.</param>
        /// <param name="distribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// An <c>numberOfRows</c>-by-<c>numberOfColumns</c> matrix with elements distributed according to the provided distribution.
        /// </returns>
        /// <exception cref="ArgumentException">If the parameter <paramref name="numberOfRows"/> is not positive.</exception>
        /// <exception cref="ArgumentException">If the parameter <paramref name="numberOfColumns"/> is not positive.</exception>
        public override Matrix Random(int numberOfRows, int numberOfColumns, IContinuousDistribution distribution)
        {
            if (numberOfRows < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "numberOfRows");
            }

            if (numberOfColumns < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "numberOfColumns");
            }

            var matrix = (SparseMatrix)CreateMatrix(numberOfRows, numberOfColumns);
            for (var i = 0; i < matrix.RowCount; i++)
            {
                for (var j = 0; j < matrix.ColumnCount; j++)
                {
                    var value = distribution.Sample();
                    if (value != 0.0)
                    {
                        matrix.SetValueAt(i, j, value);
                    }
                }
            }

            return matrix;
        }
Ejemplo n.º 28
0
 /// <summary>
 /// Create a new dense vector with values sampled from the provided random distribution.
 /// </summary>
 public static DenseVector CreateRandom(int length, IContinuousDistribution distribution)
 {
     return(new DenseVector(DenseVectorStorage <double> .OfInit(length,
                                                                i => distribution.Sample())));
 }
Ejemplo n.º 29
0
 /// <summary>
 /// Create a new diagonal matrix with diagonal values sampled from the provided random distribution.
 /// </summary>
 public static DiagonalMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     return(new DiagonalMatrix(DiagonalMatrixStorage <Complex32> .OfInit(rows, columns,
                                                                         i => new Complex32((float)distribution.Sample(), (float)distribution.Sample()))));
 }
Ejemplo n.º 30
0
 private bool ShouldMutate()
 {
     return(_mutationRateDistribution.Sample() <= _parameters.MutationRate);
 }
Ejemplo n.º 31
0
 public double Sample()
 {
     return(originalDistribution.Sample());
 }
Ejemplo n.º 32
0
 public float GetBias()
 {
     return(Convert.ToSingle(_distribution.Sample()));
 }
Ejemplo n.º 33
0
 public double Sample()
 {
     return(estimate - originalDistribution.Sample());
 }
Ejemplo n.º 34
0
 /// <summary>
 /// Create a new dense vector with values sampled from the provided random distribution.
 /// </summary>
 public static DenseVector CreateRandom(int length, IContinuousDistribution distribution)
 {
     return(new DenseVector(DenseVectorStorage <Complex32> .OfInit(length,
                                                                   i => new Complex32((float)distribution.Sample(), (float)distribution.Sample()))));
 }
 /// <summary>
 /// Create a new diagonal matrix with diagonal values sampled from the provided random distribution.
 /// </summary>
 public static DiagonalMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     return new DiagonalMatrix(DiagonalMatrixStorage<Complex>.OfInit(rows, columns,
         i => new Complex(distribution.Sample(), distribution.Sample())));
 }
Ejemplo n.º 36
0
 /// <summary>
 /// Create a new diagonal matrix with diagonal values sampled from the provided random distribution.
 /// </summary>
 public static DiagonalMatrix CreateRandom(int rows, int columns, IContinuousDistribution distribution)
 {
     return(new DiagonalMatrix(DiagonalMatrixStorage <double> .OfInit(rows, columns,
                                                                      i => distribution.Sample())));
 }
 private bool ShouldCrossover()
 {
     return(_crossoverRateDistribution.Sample() < _crossoverRate);
 }
        /// <summary>
        /// Generates matrix with random elements.
        /// </summary>
        /// <param name="numberOfRows">Number of rows.</param>
        /// <param name="numberOfColumns">Number of columns.</param>
        /// <param name="distribution">Continuous Random Distribution or Source</param>
        /// <returns>
        /// An <c>numberOfRows</c>-by-<c>numberOfColumns</c> matrix with elements distributed according to the provided distribution.
        /// </returns>
        /// <exception cref="ArgumentException">If the parameter <paramref name="numberOfRows"/> is not positive.</exception>
        /// <exception cref="ArgumentException">If the parameter <paramref name="numberOfColumns"/> is not positive.</exception>
        public virtual Matrix Random(int numberOfRows, int numberOfColumns, IContinuousDistribution distribution)
        {
            if (numberOfRows < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "numberOfRows");
            }

            if (numberOfColumns < 1)
            {
                throw new ArgumentException(Resources.ArgumentMustBePositive, "numberOfColumns");
            }

            var matrix = CreateMatrix(numberOfRows, numberOfColumns);
            CommonParallel.For(
                0,
                ColumnCount,
                j =>
                {
                    for (var i = 0; i < matrix.RowCount; i++)
                    {
                        matrix[i, j] = distribution.Sample();
                    }
                });

            return matrix;
        }