Jump to content

How to make it random but not SO random?


Recommended Posts

Hello!

I´m writing a script that has to choose a number between 00 and 10, in a "random" way. I mean, it´s not exactly randomly. I need to determine the probability of choosing each number. The normal random would be something like:

$Number = Random(0,10,1)
If $Number < 10 Then
    $Number = 0 & $Number  ; to make it appear in 2 digit format
Else
Endif
msgBox(0, "Number", "The number is " & $Number)

But, actually, I need the numbers in the middle (4, 5, 6) to be chosen more frequently than the others. And I don´t know how to do it. =(

I was looking at part of the code of Desktop Locker (near the end of the code):

Func _RandomMsg()
    Local $RandomMsg[10]
    $RandomMsg[0] = "Wrong Password!"
    $RandomMsg[1] = "Step away from the computer."
    $RandomMsg[2] = "Your not Jim."
    $RandomMsg[3] = "Give Up!"
    $RandomMsg[4] = "Don't Touch!"
    $RandomMsg[5] = "Please Enter Correct Password."
    $RandomMsg[6] = "Try Again!"
    $RandomMsg[7] = "Stop pushing my buttons."
    $RandomMsg[8] = "INS! INS!"
    $RandomMsg[9] = "Ctrl-Alt-Dipshit"
    Return $RandomMsg[Random(10)]
EndFunc   ;==>_RandomMsg

... And I think there is something there to help me. I mean, I could do something like:

$RandomMsg[0] = 01

$RandomMsg[1] = 02

$RandomMsg[2] = 03

$RandomMsg[3] = 04

$RandomMsg[4] = 04

$RandomMsg[5] = 05

$RandomMsg[6] = 05

$RandomMsg[7] = 05

$RandomMsg[8] = 06

$RandomMsg[9] = 07

...

$RandomMsg[20] = 10

And it would make some numbers appear more times in the group of possible choices. Am I right?

But I don´t know the sintaxe I should use to do that. =(

Anyone could help me?

Link to comment
Share on other sites

You pretty much answered it already:

#include <array.au3> ;so we can use _ArrayDisplay
$asNumbers = StringSplit("01|02|02|03|03|04|04|04|05|05|05|05|05|06|06|06|06|07|07|07|08|08|09","|") ;This is just an easy way to fill an array.
_ArrayDisplay($asNumbers) ;This is what your array looks like after splitting. As you can see the element count is in element 0 when using stringsplit. !THIS IS NOT ALWAYS THE CASE!
$iRnd = Random(1,$asNumbers[0],1) ;pick a randim number between the first and last element of the array, excluding the element count in element 0. (so a random number between 1 and 23)
MsgBox(0,"Your random element is:", "$asNumbers["& $iRnd & "]") ;Display the element that was randomly picked.
MsgBox(0,"The number in this element is:", $asNumbers[$iRnd]) ;display the contents of that element.

Need my sleep now. :)

Link to comment
Share on other sites

Try this (Gaussian distribution):

Global $iCnt = 1000
Global $iMax = 10

Global $aRandom[$iCnt]
Global $aNumber[$iMax + 1]

For $i = 0 To $iCnt - 1
    $aRandom[$i] = _Random(0, $iMax, True)
    $aNumber[$aRandom[$i]] += 1
Next

For $i = 0 To $iMax
    ConsoleWrite("> number " & $i & ": " & $aNumber[$i] & @TAB & " times" & @CRLF)
Next



Func _Random($fMin = 0, $fMax = 1, $bInt = False)
    Local $fTemp = ($fMax - $fMin) / 2
    Local $fGauss = _GaussRandom($fMin + $fTemp, $fTemp / 2)
    If $fGauss < $fMin Then $fGauss = $fMin
    If $fGauss > $fMax Then $fGauss = $fMax
    Switch $bInt
        Case False
            Return $fGauss
        Case Else
            Return Round($fGauss)
    EndSwitch
EndFunc   ;==>_Random


Func _GaussRandom($fMean, $fSigma)
    Local $fPI = ATan(1) * 4
    Local $fR1 = Random()
    Local $fR2 = Random()
    Local $fR = $fSigma * Sqrt(Abs(-1 * Log($fR1)))
    Local $fX1 = $fR * Cos(2 * $fPI * $fR2) + $fMean
    Local $fX2 = $fR * Sin(2 * $fPI * $fR2) + $fMean
    Switch Round(Random())
        Case 0
            Return $fX1
        Case Else
            Return $fX2
    EndSwitch
EndFunc   ;==>_GaussRandom

E

Edited by eukalyptus
Link to comment
Share on other sites

Hello!

$Number = Random(0,10,1)
If $Number < 10 Then
    $Number = 0 & $Number  ; to make it appear in 2 digit format
Else
Endif
msgBox(0, "Number", "The number is " & $Number)

...

Hi programer,

perhaps you want to take a look at StringFormat() if you don't want to use the "If $Number < 10 Then ..." thing. It's less code and you're avoiding an if-statement.

Example: StringFormat("%02s", 5) will result in "05".

:)

Regards,Hannes[spoiler]If you can't convince them, confuse them![/spoiler]
Link to comment
Share on other sites

In math class, I once learned a cool property about rolling 2 dice that the chance of the result being 2 or 12 is a lot less than rolling a result of 6, 7, 8 because there are more combinations that can result in those than for 2 or 12. I use this cool property in this script:

The performance is very good compared to the other alternatives.

#include <Array.au3>

Dim $results[11]

For $i = 0 To 10000
    $dice = _Random(0, 10, 1)
    $results[$dice] += 1
Next

ConsoleWrite(_ArrayToString($results) & @CRLF)

Func _Random($min, $max, $flag)
    $result = Random($min, $max, $flag) + Random($min, $max, $flag)
    $result /= 2
    If $flag And Mod($result, 1) <> 0 Then
        $result += Random(-1, 1, 1)/2
    EndIf
    Return $result
EndFunc

And the results speak for themselves:

176|534|861|1149|1633|1739|1426|1091|823|441|128
Edited by Manadar
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...