Choosing 3 numbers by random....process is yet too slow...how can I speed it up?
|
|
Tomfox Wiranata
Registered User
Join date: 20 Dec 2006
Posts: 80
|
02-01-2007 07:28
Hi again. I wrote the following code to create x numbers by random. Also i control that there are no numbers twice.
do { @goTO; integer random = llCeil(llFrand(45)); ZUFALLS_ZAHLEN = ZUFALLS_ZAHLEN + (string)random; nr1 = llList2String(ZUFALLS_ZAHLEN,3); nr2 = llList2String(ZUFALLS_ZAHLEN,4); nr3 = llList2String(ZUFALLS_ZAHLEN,5);
if((string)random == nr1) hits++; if((string)random == nr2) hits++; if((string)random == nr3) hits++;
if(hits == 1) { anzRandoms++; hits = 0; // jump goTO; } if(hits>1) { ZUFALLS_ZAHLEN = llDeleteSubList(ZUFALLS_ZAHLEN, -1, -1); llInstantMessage(quicktipper, "number already picked. picking new one...."); //anzRandoms--; hits = 0; jump goTO; } }while(anzRandoms < 3);
but it takes about 20s to choose those numbers. too long if u ask me.. do u know an algorithm that makes it faster? thx u all 
|
|
Stephen Zenith
Registered User
Join date: 15 May 2006
Posts: 1,029
|
02-01-2007 07:57
Here's another way of doing it - it puts the numbers 1-49 into a list, together with a random number between 0 and 1,000,000. It then sorts the list on the random number, which has the effect of sorting 1-49 into a random order. So you can then pick the first 3 numbers from the list, knowing that they're random and non-identical. It's really more of a shuffle than a random selection but it should work for you. integer MAX_NUM = 49; list numbers;
initList () { integer i; for (i = 0; i < MAX_NUM; i++) { numbers += llFrand (1000000); numbers += i; } numbers = llListSort (numbers, 2, TRUE); }
integer getNumber (integer pos) { return llList2Integer (numbers, 2 * pos + 1); }
I'm not in world, so I can't test it, but the theory should be right.
|
|
Daisy Rimbaud
Registered User
Join date: 12 Oct 2006
Posts: 764
|
02-01-2007 08:08
That's neat, I like it.
|
|
Edison Swain
Registered User
Join date: 7 Dec 2006
Posts: 51
|
02-01-2007 08:46
From: Stephen Zenith Here's another way of doing it - it puts the numbers 1-49 into a list, together with a random number between 0 and 1,000,000. It then sorts the list on the random number, which has the effect of sorting 1-49 into a random order. So you can then pick the first 3 numbers from the list, knowing that they're random and non-identical. It's really more of a shuffle than a random selection but it should work for you. integer MAX_NUM = 49; list numbers;
initList () { integer i; for (i = 0; i < MAX_NUM; i++) { numbers += llFrand (1000000); numbers += i; } numbers = llListSort (numbers, 2, TRUE); }
integer getNumber (integer pos) { return llList2Integer (numbers, 2 * pos + 1); }
I'm not in world, so I can't test it, but the theory should be right. You could create a list called "numbers" of just the numbers 1 - 49 and use something like this: list randomPicks = llList2List(llListRandomize(numbers, 1), 0, 2) This should return a new list comprised of the first 3 list items of a random sorting of "numbers", and should be sufficient. If you need more than 3, just change the last number in that line (the 2) to however many you need minus 1.
|
|
Stephen Zenith
Registered User
Join date: 15 May 2006
Posts: 1,029
|
02-01-2007 08:59
From: Edison Swain You could create a list called "numbers" of just the numbers 1 - 49 and use something like this:
list randomPicks = llList2List(llListRandomize(numbers, 1), 0, 2)
This should return a new list comprised of the first 3 list items of a random sorting of "numbers", and should be sufficient. If you need more than 3, just change the last number in that line (the 2) to however many you need minus 1. Heh, never knew there was a llListRandomize function! Nice job, with yours you can even populate the list statically, and if he needs the individual elements (rather than a list of 3 numbers) you can get rid of the llList2List call as well.
|
|
Osgeld Barmy
Registered User
Join date: 22 Mar 2005
Posts: 3,336
|
02-01-2007 21:48
//random number picker
integer how_many_to_pick = 10; integer number_cap = 100;
default { touch_start(integer total_number) { list numbers; integer counter; do { integer rnd_number = llRound(llFrand(number_cap)); if (llListFindList(numbers, [rnd_number] ) == -1) { numbers += rnd_number; ++counter; } } while (counter != how_many_to_pick); llSetText ("Your Random Numbers\n" + llDumpList2String(numbers,"\n"), <1,1,1>,1); } }
... back to the original question, altho i think a shuffle is a more effecient idea too some example stats on a script defecient simulator (my workshop)
[23:02] Object: 256 numbers [23:03] Object: completed in 67.034317 seconds
--> [23:05] Object: 100 numbers --> [23:05] Object: completed in 19.296743 seconds
[23:07] Object: 50 numbers [23:07] Object: completed in 10.978619 seconds
[23:08] Object: 25 numbers [23:08] Object: completed in 2.759773 seconds
[23:09] Object: 10 numbers [23:09] Object: completed in 1.096096 seconds
[23:10] Object: 5 numbers [23:10] Object: completed in 0.402450 seconds
|
|
Lee Ponzu
What Would Steve Do?
Join date: 28 Jun 2006
Posts: 1,770
|
pseudo code
02-02-2007 08:51
This might not be faster... Given a list [ 1 ... n ], Choose 3 without replacement
for p = 1 to 3 Pick a random number q in [p,n] Swap items at p and q
The first three are now "random" and equally probably. You can replace 3 with any number up to n
|