Posts: 358
Threads: 15
Joined: May 2003
you failed to specify the range. I've got an easy scheme to do what you ask...however, I need to know what range of numbers you are looking for!!! If you need a 10 bit number, there's no sense working with 8-bits, eh??!!!
Posts: 358
Threads: 15
Joined: May 2003
Plasma357, your scheme does indeed produce a pattern. Plotting the output of your code indicates the problem:
SCREEN 11
DEFLNG A-Z
a = TIMER
DO
hold = g
'FOR j = 1 TO 10
M = 10000
M1 = 100
B = 7821
p1 = a \ M1
p0 = a MOD M1
q1 = B \ M1
q0 = B MOD M1
c = (((p0 * q1 + p1 * q0) MOD M1) * M1 + p0 * q0) MOD M
a = (c + 1) MOD M
g = a \ M1
'PRINT g;
'NEXT
PSET (hold, g)
LOOP
Posts: 115
Threads: 6
Joined: Feb 2003
For speed purposes it precalculates 1024 'random' numbers and stores them into a array of singles.
--Code Begins--
FUNCTION Rand% (Max%)
STATIC Init%, RandomNums() AS SINGLE, Cnt%
IF Init% = 0 THEN
DIM RandomNums(1023) AS SINGLE
FOR I% = 0 TO 1023
NewSeed# = TIMER / 60
Temp# = (((NewSeed# * LastSeed#) - I%) MOD 100) / 100
LastSeed# = (NewSeed# + I% - Temp#)
RandomNums(I%) = Temp#
NEXT
Init% = -1
END IF
Rand% = RandomNums(Cnt%) * Max%
Cnt% = (Cnt% + 1) AND 1023
END FUNCTION
very F***ing song remains the same
To everyone who sucks-up for the fame
Out of strength you know we speak the truth
Every trend that dies is living proof
MasterMinds Software
Posts: 1,752
Threads: 21
Joined: Jun 2002
Quote:Plasma357, your scheme does indeed produce a pattern. Plotting the output of your code indicates the problem:
Heh, it's not exactly "mine", and you'll be hard-pressed to find a random number generator with no pattern.
Posts: 358
Threads: 15
Joined: May 2003
[/quote]Heh, it's not exactly "mine", and you'll be hard-pressed to find a random number generator with no pattern.[/quote]
Plasma357, I respectfully disagree about the no pattern business;-) This one will repete...but not for a LONG time...like...if you are generating a billion numbers/second, it'd take something like 10^100 times longer than the age of the universe...it won't repete in your life time...also...if it does, just make it a bit wider, say 60,000 wide (eg DIM a(-32000 to 32000) AS INTEGER)
I don't show explicitly how to get a random number from this file, however it's straight forward. Just grab a bit sequence from the array (eg the first 32 bits of the array for a long integer) then convert it and stick it in a variable. When you need another one, either take the next block of 32 bits in the row, or step down a row.
Code: 'random number generator--Joe Campbell
'This pattern will repeat...it's 640-bit, so there are only
'4.6x10^192 possible states!!! This pattern will only visit some
'fraction of the possible states...perhaps 25% Still...you want a
'random sequence of 2-byte integers??? choose any screen position of the
'developed field and take 16-bits...move down a line then take another 16.
'the numbers represented will pass every test of randomness. The center
'column of this unbounded automata is used by Mathmatica for generate random
'numbers. See Stephen Wolfram's "A New Kind of Science". I have implemented
'a strong secret key encryption using this so-called "rule 30" automata.
SCREEN 11
CLS
DIM a(1 TO 640) AS INTEGER
DIM b(1 TO 640) AS INTEGER
a(320) = 1 'starting condition...simplist case...a single bit in a field of zeros
'output is "just as random" as a for a more complex seed.
'RANDOMIZE TIMER: FOR t = 1 TO 640: a(t) = RND: NEXT t 'this is the "maximally random" starting condition
DO
FOR y = 1 TO 480
b(1) = (a(640) XOR (a(1) OR a(2))) 'special case wrapping
FOR x = 2 TO 639
b(x) = (a(x - 1) XOR (a(x) OR a(x + 1))) 'normal case
NEXT x
b(640) = (a(639) XOR (a(640) OR a(1))) 'special case wrapping
FOR x = 1 TO 640
PSET (x, y), b(x)
SWAP a(x), b(x)
NEXT x
NEXT y
LOOP
Posts: 3,368
Threads: 195
Joined: Jan 2003
Nope, nope.
Your random number generator has a pattern that is created from the code.
The code *is* the pattern.
Peace cannot be obtained without war. Why? If there is already peace, it is unnecessary for war. If there is no peace, there is already war."
Visit www.neobasic.net to see rubbish in all its finest.
Posts: 358
Threads: 15
Joined: May 2003
Quote:Nope, nope.
Your random number generator has a pattern that is created from the code.
The code *is* the pattern.
Agamemnus,
I guess pattern is the wrong word...every sequence of numbers has a pattern...it's own. What I meant was that a pattern would be seen if the "random" numbers were plotted. That is, the output of the random number generator can be somehow represented with less data than the output itself. It's really a philosophical question. If every detail of a system is known...can one predict the outcome of that system? I suspect the answer is yes, even for radioactive decay...however, the amount of computation required should be equivalent to letting the system develop on it's own. As such...it is basically unanswerable without taking a wait and see approach. The same is true for the "rule 30" automata.
I adjusted the code to make it a random number generator with output in the 0 to 1 range, double precision. Of course if you seed it with the same value you will get the same sequence of numbers. However, that doesn't change the fact that the number sequence will stand up to any test for randomness that you can throw at it!!
Change the seed, and the sequence will be just as "random"...but a different sequence. Evaluate the numbers...you will find no local or long-distance coorelation between the numbers.
the other submissions do not pass the test:
SCREEN 11
DO
PSET(RND*640, RND*480)
LOOP
Furthermore, some of them rely on TIMER as input...which is essentially a random input to the system. My method is different. the only input is a single bit, and the output appears to follow no pattern...although it is not "random" in that it is reproducable. I should have used function, but wrote it with calls instead...sorry for the awkwardness...Here's the code...It doesn't need to be this long, but it helps make it easier to understand.
Code: DECLARE SUB seed (a%(), randomnum#, b%(), maxwidth%)
DECLARE SUB stepautomata (a%(), randomnum#, b%(), maxwidth%)
DECLARE SUB rando (a%(), randomnum#, b%(), maxwidth%)
DEFINT A-Z
SCREEN 0
maxwidth% = 1000 'Set maxwidth% as big as you want, but at least as big
'as the bit-depth of the random number...in this case 32 is absolute minimum.
'if you make it small, the automata will repete and non-random output will
'be observed.
DIM a(0 TO maxwidth%) AS INTEGER 'arrays that hold automata
DIM b(0 TO maxwidth%) AS INTEGER 'a() is last complete line, b() is next line
CALL seed(a%(), randomnum#, b%(), maxwidth%)
'after this line, random numbers are available with CALL rando
'for example, the following loop fills screen with random dots.
SCREEN 11
DO
CALL rando(a%(), randomnum#, b%(), maxwidth%) 'get a random number...
x = 640 * randomnum# 'and scale it for your purposes
CALL rando(a%(), randomnum#, b%(), maxwidth%) 'get another...
y = 480 * randomnum#
PSET (x, y)
LOOP UNTIL INKEY$ <> ""
END
SUB rando (a%(), randomnum#, b%(), maxwidth%) STATIC
IF position + 32 > maxwidth% THEN 'checks to see if a new line is needed
CALL stepautomata(a%(), randomnum#, b%(), maxwidth%) 'update the array a%()
position = 0
END IF
grabaword# = 0 'reset value between calls
FOR x = 0 TO 31 'bit-depth of random number
grabaword# = grabaword# + (a%(position) * (2 ^ x)) 'grab a 32 bit chunk of a%() and convert to a double precision number
position = position + 1 'keep track of where you are on in array
NEXT x
'note...x=32 here
randomnum# = grabaword# / ((2 ^ x) - 1) 'normalize so that randomnum#
'will be in the range 0 to 1
END SUB 'just like the basic function RND
SUB seed (a%(), randomnum#, b%(), maxwidth%) STATIC
PRINT "seeding"
'this is needed to get array filled with indeterminate data.
a%(0) = 1 'starting condition...simplest case...a single "1" in a
'field of zeros. The output is "just as random" as with
'a more complex seed. Try the next line to see this.
'this is the "maximally random" starting condition:
'RANDOMIZE TIMER: FOR t = 0 TO maxsize%: a(t) = RND: NEXT t
FOR t = 0 TO maxwidth% \ 2 '2 is used b/c automata expands in both directions
CALL stepautomata(a%(), randomnum#, b%(), maxwidth%)
NEXT t
CLS
END SUB
SUB stepautomata (a%(), randomnum#, b%(), maxwidth%) STATIC
'this steps the automata forward...and is the source of the randomness
b%(0) = (a%(maxwidth%) XOR (a%(0) OR a%(1))) 'special case wrapping left
FOR x = 1 TO maxwidth% - 1
b%(x) = (a%(x - 1) XOR (a%(x) OR a%(x + 1))) 'normal case
NEXT x
b%(maxwidth%) = (a%(maxwidth% - 1) XOR (a%(maxwidth%) OR a%(0))) 'special case wrapping right
FOR x = 0 TO maxwidth% 'puts new values in a%()
SWAP a%(x), b%(x)
NEXT x
END SUB
Posts: 3,368
Threads: 195
Joined: Jan 2003
Oh.....hm... ok.
I might find a correlation..............................................
Peace cannot be obtained without war. Why? If there is already peace, it is unnecessary for war. If there is no peace, there is already war."
Visit www.neobasic.net to see rubbish in all its finest.
Posts: 358
Threads: 15
Joined: May 2003
Quote:Oh.....hm... ok.
I might find a correlation..............................................
I seriously doubt it ;-)
I may not be able to spell correlation, but I sure can tell you that numbers that my program spits out don't have one;-)
Cheers. Do I win the challenge, or not? The other entries don'pass the:
PSET (random(x), random(y))
test...or they use timer to seed...mine passes. Any entries that use another scheme and pass??
Posts: 115
Threads: 6
Joined: Feb 2003
I didn't have time to see how long it takes for a 'pattern' to form... but it seems pretty 'random' and on speed test's it was as fast as qb's RND when compiled and sometimes slightly faster.
both averaging around 88000 numbers a second
highest my routine got so far was 92534.
keep in minf these numbers are based on the program being compiled, my routine averaged around 64000 uncompiled.
DEFINT A-Z
FUNCTION Rand (Min, Max)
STATIC Cnt AS LONG, Cnt2 AS LONG, LastMin, LastMax
STATIC LastValue
Ran = Max - Min
Cnt = (Cnt + (LastMin + LastMax)) AND 32767
Cnt2 = (Cnt2 + ((Cnt + (Max + Min)))) AND 32767
D& = ((Cnt + Cnt2) + (Ran + Min))
D2 = (D& + LastValue) MOD (Ran + 1) + Min
Rand = D2
LastValue = D2
LastMin = Min
LastMax = Max
END FUNCTION
very F***ing song remains the same
To everyone who sucks-up for the fame
Out of strength you know we speak the truth
Every trend that dies is living proof
MasterMinds Software
|