Non-Uniform Random Numbers in Visual Basic QuickStart Sample

Illustrates how to generate random numbers from a non-uniform distribution in Visual Basic.

This sample is also available in: C#, F#, IronPython.

Overview

This QuickStart sample demonstrates how to generate random numbers from non-uniform probability distributions using Numerics.NET.

The sample specifically illustrates the relationship between exponential and Poisson distributions in modeling events over time. It uses an exponential distribution to generate times between events, and then compares the resulting frequency of events per time unit with the theoretical Poisson distribution.

The code shows how to:

  • Create and configure specific probability distributions (Exponential and Poisson)
  • Use the MersenneTwister random number generator
  • Generate random samples from a probability distribution
  • Collect and analyze statistical data from the generated samples
  • Compare empirical results with theoretical expectations

This practical example helps understand both the mechanics of generating non-uniform random numbers and how different probability distributions relate to each other in modeling real-world phenomena.

The code

Imports Numerics.NET.Statistics.Distributions
Imports Numerics.NET.Random

    ' Illustrates generating non-uniform random numbers
    ' using the classes in the Numerics.NET.Statistics.Random
    Module NonUniformRandomNumbers

        Sub Main()
        ' The license is verified at runtime. We're using
        ' a 30 day trial key here. For more information, see
        '     https://numerics.net/trial-key
        Numerics.NET.License.Verify("your-trial-key-here")

        ' Random number generators and the generation
        ' of uniform pseudo-random numbers are illustrated
        ' in the UniformRandomNumbers QuickStart Sample.

        ' In this sample, we will generate numbers from
        ' an exponential distribution, and compare summary
        ' results to what would be expected from
        ' the corresponding Poisson distribution.

        Dim meanTimeBetweenEvents As Double = 0.42

        ' We will use the exponential distribution to generate the time
        ' between events. The number of events per unit time follows
        ' a Poisson distribution.

        ' The parameter of the exponential distribution is the time between events.
        Dim exponential As ExponentialDistribution =
                New ExponentialDistribution(meanTimeBetweenEvents)
        ' The parameter of the Poisson distribution is the mean number of events
        ' per unit time, which is the reciprocal of the time between events:
        Dim poisson As PoissonDistribution = New PoissonDistribution(1 / meanTimeBetweenEvents)

        ' We use a MersenneTwister to generate the random numbers:
        Dim random As New MersenneTwister

        ' The totals array will track the number of events per time unit.
        Dim totals As Integer() = New Integer(14) {}

        Dim currentTime As Double = 0
        Dim endOfCurrentTimeUnit As Double = 1
        Dim eventsInUnit As Integer = 0
        Do While (currentTime < 100000)
            Dim timeBetween As Double = exponential.Sample(random)
            ' Alternatively, we could have written
            '   timeBetween = random.NextDouble(exponential)
            ' which would give an identical result.
            currentTime += timeBetween
            Do While (currentTime > endOfCurrentTimeUnit)
                If (eventsInUnit >= totals.Length) Then
                    eventsInUnit = totals.Length - 1
                End If
                totals(eventsInUnit) = totals(eventsInUnit) + 1
                eventsInUnit = 0
                endOfCurrentTimeUnit = endOfCurrentTimeUnit + 1
            Loop
            eventsInUnit = eventsInUnit + 1
        Loop

        ' Now print the totals
        Console.WriteLine("# Events    Actual  Expected")
        For i As Integer = 0 To totals.Length - 1
            Dim expected As Integer = Convert.ToInt32(100000 * poisson.Probability(i))
            Console.WriteLine("{0,8}  {1,8}  {2,8}", i, totals(i), expected)
        Next

        Console.Write("Press any key to exit.")
        Console.ReadLine()

    End Sub

End Module