Reputation: 63
I could try and explain what this code is for and why the output is the way it is, but it will take forever.
function Get90nums(G90_TC)
if NOT isNumeric(G90_TC) then exit function : G90_TC=int(G90_TC) : if G90_TC>6 OR G90_TC<1 then exit function
dim G90_BA : G90_BA="" : dim G90_CC : G90_CC=false : dim G90_NC : G90_NC=0 : dim G90_RC : G90_RC=0 : dim G90_TBL : G90_TBL=0
do until G90_CC
randomize : G90_RN=int((90)*rnd+1)
if inStr(G90_BA,"["&G90_RN&"]")=0 then
if G90_NC=5 then
G90_BA=G90_BA&"[91][91][91][91]NL" : G90_RC=G90_RC+1 : G90_NC=0
if G90_RC=3 then
G90_TBL=G90_TBL+1
G90_RC=0
end if
else
G90_BA=G90_BA&"["&G90_RN&"]" : G90_NC=G90_NC+1
end if
end if
if G90_TBL=G90_TC then G90_CC=true : Get90nums=G90_BA
loop
end function
response.write Get90nums(1)
If you run the function as Get90nums(1)
it will return something along the lines of:
[22][15][85][31][14][91][91][91][91]NL[40][10][9][77][54][91][91][91][91]NL[49][71][6][64][4][91][91][91][91]NL
I say "something along the lines" because the output is random. Ignore the fact the numbers are in brackets, ignore all the "91's" and the "NL's", and what you get is:
[22][15][85][31][14][40][10][9][77][54][49][71][6][64][4]
That's 15 unique random numbers between 1 and 90, no number is repeated.
Run the function as Get90nums(5)
and you will get 75 unique numbers between 1 and 90.
However, if you run Get90nums(6)
, rather than returning all 90 numbers, it just get's stuck in an infinite loop, and I have no idea why.
Can anybody please shine some light on this, it's driving me crazy!
Thanks
Upvotes: 0
Views: 563
Reputation: 63
I fixed it.
Instead of generating a random number each time I put all 90 numbers into an array beforehand and shuffled it.
UK bingo differs a lot from US bingo. You get six 3*9 cards. Each row has 5 numbers spread out and in ascending order. There are 90 numbers overall and no duplicates.
It's clearly a very early draft, but if you want to play 6 card UK bingo (it works with 1 to 6 cards) here's the script:
<%@LANGUAGE="VBSCRIPT" CODEPAGE="65001"%>
<%
'----------------------------------------------------------------------------------
Dim array90(89)
for x = 0 to 89
array90(x)=x+1
next
Arr90=ArrReOrder(array90)
'----------------------------------------------------------------------------------
function Get90nums(G90_TC)
if NOT isNumeric(G90_TC) then exit function:G90_TC=G90_TC:if G90_TC>6 OR G90_TC<1 then exit function
dim G90_BA:G90_BA="":dim G90_CC:G90_CC=false:dim G90_NC:G90_NC=0:dim G90_RC:G90_RC=0:dim G90_TBL:G90_TBL=0
for x=0 to (G90_TC*15)-1
G90_RN=Arr90(x)
G90_BA=G90_BA&"["&G90_RN&"]":G90_NC=G90_NC+1
if G90_NC=5 then
G90_BA=G90_BA&"[91][91][91][91]NL":G90_RC=G90_RC+1:G90_NC=0
if G90_RC=3 then
G90_TBL=G90_TBL+1
G90_RC=0
end if
end if
if G90_TBL=G90_TC then G90_CC=true:Get90nums=G90_BA
next
end function
'----------------------------------------------------------------------------------
function ArrReOrder(aArray)
Dim iUpper,iLower,iLoop,iSwapPos,varTmp
iUpper=UBound(aArray):iLower=LBound(aArray)
randomize Timer
for iLoop=iLower to iUpper
iSwapPos=Int(Rnd*(iUpper+1))
varTmp=aArray(iLoop)
aArray(iLoop)=aArray(iSwapPos)
aArray(iSwapPos)=varTmp
next
ArrReOrder=aArray
end function
'----------------------------------------------------------------------------------
sub arrNumericalAsc(arrArray)
Dim row,j,StartingKeyValue,NewKeyValue,swap_pos
for row=0 to uBound(arrArray)-1
if NOT arrArray(row)=91 then
StartingKeyValue=int(arrArray(row))
NewKeyValue=int(arrArray(row))
swap_pos=row
for j=row+1 to uBound(arrArray)
if int(arrArray(j)) < int(NewKeyValue) then
swap_pos=j
NewKeyValue=arrArray(j)
end if
next
if int(swap_pos) <> row then
arrArray(swap_pos)=int(StartingKeyValue)
arrArray(row)=int(NewKeyValue)
end if
end if
next
end sub
'
'----------------------------------------------------------------------------------
Dim RC,NLarray,CommaArray,lineNums:lineNums=Get90nums(6):RC=0
lineNums=replace(lineNums,"[","")
lineNums=replace(lineNums,"]",",")
NLarray=split(lineNums,",NL")
for y=0 to uBound(NLarray)
RC=RC+1
if RC=1 AND NOT y=uBound(NLarray) then Response.Write("<table width=""0%"" border=""1"" cellspacing=""0"" cellpadding=""10"">")&VBcrlf
CommaArray=split(NLarray(y),",")
CommaArray=ArrReOrder(CommaArray)
arrNumericalAsc CommaArray
for z=0 to uBound(CommaArray)
if z=0 then Response.Write(" <tr>")&VBcrlf
if CommaArray(z)=91 then CA_val=" " else CA_val=CommaArray(z)
Response.Write(" <td width=""30"" align=""center"">" & CA_val & "</td>")&VBcrlf
if z=uBound(CommaArray) then Response.Write(" </tr>")&VBcrlf
next
if RC=3 then Response.Write("</table>"&VBcrlf&VBcrlf&"<br><br>")&VBcrlf&VBcrlf:RC=0
next
%>
Upvotes: 1
Reputation: 12847
Move the randomize out of the loop and notice the change to the G90_RN line, use CInt over Int:
randomize
do until G90_CC
G90_RN=CInt((90*Rnd())+1)
if inStr(G90_BA,"["&G90_RN&"]")=0 then
if G90_NC=5 then
G90_BA=G90_BA&"[91][91][91][91]NL" : G90_RC=G90_RC+1 : G90_NC=0
if G90_RC=3 then
G90_TBL=G90_TBL+1
G90_RC=0
end if
else
G90_BA=G90_BA&"["&G90_RN&"]" : G90_NC=G90_NC+1
end if
end if
if G90_TBL=G90_TC then G90_CC=true : Get90nums=G90_BA
loop
Upvotes: 0
Reputation: 11018
Once G90_BA has filled up with 90 unique random number in the range 1..90, the expression inStr(G90_BA,"["&G90_RN&"]")=0 will consistently fail. At that point, G90_TBL will no longer be increased. Possibly it is then stuck at a value less than 6, so it will never become equal to G90_TC, G90_CC is never set to true, and the loop never ends. An alternative explanation would be that it is taking increasingly long to find unused numbers to fill the last few slots in the list. In other words, it is just slow. Try it in a debugger and see.
BTW, it is OK if takes forever to explain the code's purpose, but it is not OK if it takes forever to explain what this code is doing. Please refactor.
Upvotes: 0