在 Powershell 中,如何生成具有指定均值的随机变量(指数)?

In Powershell, How to generate a random variable (exponential) with a specified mean?

我正在尝试编写一个基本模拟(队列),它依赖于生成随机外变量。虽然 Powershell 提供了一个 Get-Random 函数,您可以指定一个最小值和一个最大值,但它没有任何接近 Python 的 random.expovariate(lambd) 函数。

据推测这是我应该遵循的模型:log(1-$u)/(−λ)

出色的 Python 文档对此有如下说明:

"Exponential distribution. lambd is 1.0 divided by the desired mean. It should be nonzero. (The parameter would be called “lambda”, but that is a reserved word in Python.) Returned values range from 0 to positive infinity if lambd is positive, and from negative infinity to 0 if lambd is negative.". In another description, "expovariate() produces an exponential distribution useful for simulating arrival or interval time values for in homogeneous Poisson processes such as the rate of radioactive decay or requests coming into a web server.

The Pareto, or power law, distribution matches many observable phenomena and was popularized by Chris Anderon’s book, The Long Tail. The paretovariate() function is useful for simulating allocation of resources to individuals (wealth to people, demand for musicians, attention to blogs, etc.)."

我试过用 Powershell 写这个,但我的发行版还差得远。如果我输入均值为 3,我得到的结果与我应该从均值为 1 得到的结果非常接近。我的代码密切模仿 John D. Cook's SimpleRNG C# library.

function GetUniform #GetUint
{
    Return Get-Random -Minimum -0.00 -Maximum 1
}



# Get exponential random sample with specified mean
function GetExponential_SpecMean{
param([double]$mean)

    if ($mean -le 0.0)
    {
                Write-Host "Mean must be positive. Received $mean."
                
            }
    $a = GetExponential
    $R = $mean * $a
    Return $R
}


# Get exponential random sample with mean 1
function GetExponential
{
    $x = GetUniform
    Return -[math]::log10(1-$x) # -Math.Log( GetUniform() );
}

cls
$mean5 = 1
$rangeBottom = 0.0
$rangeTop = 1.0

$j = 0
$k = 0
$l = 0

    for($i=1; $i -le 1000; $i++){
        $a = GetExponential_SpecMean $mean5
   
        if($a -le 1.0){Write-Host $a;$j++}
        if($a -gt 1.0){Write-Host $a;$k++}
        if(($a -gt $rangeBottom) -and ($a -le $rangeTop)){#Write-Host $a;
        $l++}
    
        Write-Host "                      -> $i "
        }

Write-Host "One or less: $j"
Write-Host "Greater than one: $k"
Write-Host "Total in range between bottom $rangeBottom  and top $rangeTop : $l"

对于 1000 的样本和 1 的均值 ($mean5),我应该得到(我相信)500 个等于或小于 1.0 的结果和 500 个大于 1.0 的结果(1:1 比率),但是我我得到的比率约为 9:1,平均值为 1,比率约为 53:47,平均值为 3.

在这个 Stack Overflow 问题中有一些讨论具有很好的背景,但它并不特定于 Powershell:Pseudorandom Number Generator - Exponential Distribution

我看到您使用的是 [Math]::log10(),它是以 10 为底的对数,我在您的链接中看到的所有函数都使用自然对数。您应该使用 [Math]::Log() 代替 log10。应该做的。