Sign in to follow this  
Followers 0
programer

How to make it random but not SO random?

6 posts in this topic

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?

Share this post


Link to post
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. :)

Share this post


Link to post
Share on other sites

#3 ·  Posted (edited)

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

Share this post


Link to post
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]

Share this post


Link to post
Share on other sites

#5 ·  Posted (edited)

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

Share this post


Link to post
Share on other sites

Very good sugestions! I´m goona study these codes and try to find the best solution!

Thank you all!!!

Share this post


Link to post
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
Sign in to follow this  
Followers 0