Update
Why on earth is making a math stack so dam hard.
Here's the issue, It solves equasions. Oh yes, division, up until the very last "/"
whatever I give up for now I can do it i'm so tired though goodnight
TinySB Interpreter in the works
Root / Talk About Programs / [.]
CoinzReturnsCreated:
Update
I was wrong it isn't simpler than I thought.. Infact I had a very strong idea of the steps I need to take to accomplish the math stack parser.
I'm not done yet! Look out.
Here's some not so pretty Eye candy the image was edited to explain what's going on
Here I've got some test code that finally divides inside the equasion and replaces the old text with the new values..
This requires some initialization..
I can't even begin to explain why it works but I indeed did use quite a loopy method.
Maybe that's because I've been drinking a little *teehee* of course..
Well on with it I guess
Basically it can divide!
It's doing multiple things
It's making a list of all the integers found in the string
It's making a list of all the operands found in the string
It's using a rule that there should be exactly one more integer than operand in the whole of both sets.
It's using a pair value rule
I'm treating each operation as a pair of 3 values.
"50/100" is a pair
"20/1000" is a pair
This is the logic I used
The next thing it does is it uses the fact it can extract the variable integers from the original string to convert them to strings.
Once it converts the first value and the second value to strings
It gets their length.
It uses the iterator that finds the first occuring "/" symbol's place in the string as the start point.
It then subtracts the start point from the first value's string length to get something called extract_st
it then sets the firstvalue_st, firstvalue_nd
secondvalue_st and secondvalue_nd variables which represent where in the string these values lengths start and end.
By getting all of this information I have a way (without having to do match cases specifically on the integer values)
to get the exact place inside the string where they occur
Then since I already have the values themselves and I know what the oprand is I can simply set this
result = first_value / second_value
result_string$ = str$(result) and I convert the result back into a string
next, I replace what was removed from the string like this
removed_string$ = mid$(inputstr$, extract_st, len(inputstr$)-extract_nd)
by doing this I always get the exact location of the entire equasion no matter the length or how many numbers are in it
Next.
I end up with this:
inputstr$ = replace$(inputstr$, removed_string$, "!", 0, 0, 1) the last parameter is the replace once only case
now later I do this
inputstr$ = replace$(inputstr$, "!", result_string$, 0, 0, 1) //And this basically captures the result and re-injects it into the string
Okay now that i'm not all frustrated here's the explanation of solving the operand stack i've coded up.
It's not all pretty but assume I have an integer list array
and an operand list array
I can't get this to fully work:
Basically the method i'm using steps through the operand list and the integer list, finds the first occurence of the target operand in the operand list
sets the values of the first int and the second int from the integer list
after that, it iterates through the source string itself, to find the first occurence of the same operand
Then it sets the starting position of the first operand in the source string to the iteration variable GX
Once this is set
It converts the first value and the second value to strings
It uses the length of the first value subtracted from the start position of the first operand to get the start position of the whole sub equasion
it uses the length of the second value added to the start position of the first operand to get the end position of the whole sub equasion
it then sets a string called removed$ to mid$(source_string$, extractst, extractnd)
It then gets the result
result =firstvalue/secondvalue
after this it does a single replace on the source string
inputstr$ = replace$(inputstr$, removed$, "!", 0, 0, 1) //the last 1 is for single case only
after this is done
the original division formula that it found is replaced by a single "!"
after this I inject the solution of that equasion back into the string where the "!" is
replace$(inputstr$, "!", removed$, 0, 0, 1)
//after this I exit the for loop of GX
exitfor
Endif //like 3 if statements come before all this to ensure it only does it in cases where the operand was found and calculated
Update
I think I finally did it.
I have ONE source code, with a hard coded algorithm to test with..
It can resize the original entrants using the rule first value = iterator, operand = iterator, and second value = iterator+1 and result is integerarray(t+1)
or integerarray( iterator+1)
Yes..
and because it shifts all the numbers around the only thing I had left to do was to flag the ones to be removed..
both integers and numbers
leaving only valid integers in the list of ints and only valid integers in the list of ints
with the operands list still being 1 less in length or numerical indexes than the integer list
my god this was hard to solve... took nearly 3 days lol
But I basically here and for the most part have solved all the math stack problems.
REJOICE TinySB development is near completion! (for the alpha anyways... *ahem* )
Let's get some cake.. I mean coke.. I mean coca cola.
Here's the frikkin awesome code that runs inside PlayBasic
I'm not posting it in the code tag as it would probably mangle it.
Spoiler
; PROJECT : TestingAgain ; AUTHOR : Microsoft ; CREATED : 5/24/2016 ; EDITED : 5/24/2016 ; --------------------------------------------------------------------- //I don't want to write the functions so i'll define some of these things specifically inputstr$="1800-3/3+28*8/9-8/2" //inputstr$="1800-1+28*8/9-8/2" //inputstr$="1800-1+224/9-8/2" //inputstr$="1800-1+24-8/2" //inputstr$="1800-1+24-4" dim intslist(8) intslist(1)=1800 intslist(2)=3 intslist(3)=3 intslist(4)=28 intslist(5)=8 intslist(6)=9 intslist(7)=8 intslist(8)=2 dim intslist$(8) //make a list of the ints that are flagged for t=1 to 8 intslist$(t)=str$(intslist(t)) next t dim operandslist$(7) operandslist$(1)="-" operandslist$(2)="/" operandslist$(3)="+" operandslist$(4)="*" operandslist$(5)="/" operandslist$(6)="-" operandslist$(7)="/" //first divide or multiply for divmult=1 to 7 if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult //Now we have our flag list //first count the remaining operands dim newlist$(1) for tt=1 to 7 if operandslist$(tt) !="!" inc operandcount redim newlist$(operandcount) newlist$(operandcount) = operandslist$(tt) endif next tt dim newintlist$(1) for tt=1 to 8 if intslist$(tt) !="!" inc intcount redim newintlist$(intcount) newintlist$(intcount) = intslist$(tt) endif next tt //after generating a new list proper for this //We want to copy it to the old lists redim intslist(intcount) redim operandslist$(operandcount) for tt=1 to intcount intslist(tt) = val (newintlist$(tt)) next tt for gg=1 to operandcount operandslist$(gg) = newlist$(gg) next gg //finally attempt solving for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) print inputstr$ print "hi" waitkey waitnokey psub getchar(str_$, ptr) char_$ = mid$(str_$, ptr, 1) endpsub char_$ psub divide(t, inputstr$) found=false if operandslist$(t) = "/" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value / second_value #print "Divide " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="/" //symbol found operandslist$(t)="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ #print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub multiply(t, inputstr$) found=false if operandslist$(t) = "*" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value * second_value #print "Multiply " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="*" //symbol found operandslist$(t) ="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub subtract(t, inputstr$) found=false if operandslist$(t) = "-" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value - second_value #print "subtract " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="-" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub add(t, inputstr$) found=false if operandslist$(t) = "+" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value + second_value #print "Add " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="+" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$Update I think I finally did it. I have ONE source code, with a hard coded algorithm to test with.. It can resize the original entrants using the rule first value = iterator, operand = iterator, and second value = iterator+1 and result is integerarray(t+1) or integerarray( iterator+1) Yes.. and because it shifts all the numbers around the only thing I had left to do was to flag the ones to be removed.. both integers and numbers leaving only valid integers in the list of ints and only valid integers in the list of ints with the operands list still being 1 less in length or numerical indexes than the integer list my god this was hard to solve... took nearly 3 days lol But I basically here and for the most part have solved all the math stack problems. REJOICE TinySB development is near completion! (for the alpha anyways... *ahem* ) Let's get some cake.. I mean coke.. I mean coca cola. Here's the frikkin awesome code that runs inside PlayBasicDoesn't smileBASIC use double = when querying? Nice job btw.I'm not posting it in the code tag as it would probably mangle it.Spoiler
; PROJECT : TestingAgain ; AUTHOR : Microsoft ; CREATED : 5/24/2016 ; EDITED : 5/24/2016 ; --------------------------------------------------------------------- //I don't want to write the functions so i'll define some of these things specifically inputstr$="1800-3/3+28*8/9-8/2" //inputstr$="1800-1+28*8/9-8/2" //inputstr$="1800-1+224/9-8/2" //inputstr$="1800-1+24-8/2" //inputstr$="1800-1+24-4" dim intslist(8) intslist(1)=1800 intslist(2)=3 intslist(3)=3 intslist(4)=28 intslist(5)=8 intslist(6)=9 intslist(7)=8 intslist(8)=2 dim intslist$(8) //make a list of the ints that are flagged for t=1 to 8 intslist$(t)=str$(intslist(t)) next t dim operandslist$(7) operandslist$(1)="-" operandslist$(2)="/" operandslist$(3)="+" operandslist$(4)="*" operandslist$(5)="/" operandslist$(6)="-" operandslist$(7)="/" //first divide or multiply for divmult=1 to 7 if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult //Now we have our flag list //first count the remaining operands dim newlist$(1) for tt=1 to 7 if operandslist$(tt) !="!" inc operandcount redim newlist$(operandcount) newlist$(operandcount) = operandslist$(tt) endif next tt dim newintlist$(1) for tt=1 to 8 if intslist$(tt) !="!" inc intcount redim newintlist$(intcount) newintlist$(intcount) = intslist$(tt) endif next tt //after generating a new list proper for this //We want to copy it to the old lists redim intslist(intcount) redim operandslist$(operandcount) for tt=1 to intcount intslist(tt) = val (newintlist$(tt)) next tt for gg=1 to operandcount operandslist$(gg) = newlist$(gg) next gg //finally attempt solving for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) print inputstr$ print "hi" waitkey waitnokey psub getchar(str_$, ptr) char_$ = mid$(str_$, ptr, 1) endpsub char_$ psub divide(t, inputstr$) found=false if operandslist$(t) = "/" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value / second_value #print "Divide " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="/" //symbol found operandslist$(t)="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ #print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub multiply(t, inputstr$) found=false if operandslist$(t) = "*" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value * second_value #print "Multiply " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="*" //symbol found operandslist$(t) ="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub subtract(t, inputstr$) found=false if operandslist$(t) = "-" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value - second_value #print "subtract " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="-" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub add(t, inputstr$) found=false if operandslist$(t) = "+" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value + second_value #print "Add " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="+" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$
This is written inside PlayBasic not SmileBasic. Final update, short internet outage messed with me but yeah I now have basically the main functionality originally plus i've reduced it into a simple calculate function like so:Update I think I finally did it. I have ONE source code, with a hard coded algorithm to test with.. It can resize the original entrants using the rule first value = iterator, operand = iterator, and second value = iterator+1 and result is integerarray(t+1) or integerarray( iterator+1) Yes.. and because it shifts all the numbers around the only thing I had left to do was to flag the ones to be removed.. both integers and numbers leaving only valid integers in the list of ints and only valid integers in the list of ints with the operands list still being 1 less in length or numerical indexes than the integer list my god this was hard to solve... took nearly 3 days lol But I basically here and for the most part have solved all the math stack problems. REJOICE TinySB development is near completion! (for the alpha anyways... *ahem* ) Let's get some cake.. I mean coke.. I mean coca cola. Here's the frikkin awesome code that runs inside PlayBasicDoesn't smileBASIC use double = when querying? Nice job btw.I'm not posting it in the code tag as it would probably mangle it.Spoiler
; PROJECT : TestingAgain ; AUTHOR : Microsoft ; CREATED : 5/24/2016 ; EDITED : 5/24/2016 ; --------------------------------------------------------------------- //I don't want to write the functions so i'll define some of these things specifically inputstr$="1800-3/3+28*8/9-8/2" //inputstr$="1800-1+28*8/9-8/2" //inputstr$="1800-1+224/9-8/2" //inputstr$="1800-1+24-8/2" //inputstr$="1800-1+24-4" dim intslist(8) intslist(1)=1800 intslist(2)=3 intslist(3)=3 intslist(4)=28 intslist(5)=8 intslist(6)=9 intslist(7)=8 intslist(8)=2 dim intslist$(8) //make a list of the ints that are flagged for t=1 to 8 intslist$(t)=str$(intslist(t)) next t dim operandslist$(7) operandslist$(1)="-" operandslist$(2)="/" operandslist$(3)="+" operandslist$(4)="*" operandslist$(5)="/" operandslist$(6)="-" operandslist$(7)="/" //first divide or multiply for divmult=1 to 7 if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult //Now we have our flag list //first count the remaining operands dim newlist$(1) for tt=1 to 7 if operandslist$(tt) !="!" inc operandcount redim newlist$(operandcount) newlist$(operandcount) = operandslist$(tt) endif next tt dim newintlist$(1) for tt=1 to 8 if intslist$(tt) !="!" inc intcount redim newintlist$(intcount) newintlist$(intcount) = intslist$(tt) endif next tt //after generating a new list proper for this //We want to copy it to the old lists redim intslist(intcount) redim operandslist$(operandcount) for tt=1 to intcount intslist(tt) = val (newintlist$(tt)) next tt for gg=1 to operandcount operandslist$(gg) = newlist$(gg) next gg //finally attempt solving for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) print inputstr$ print "hi" waitkey waitnokey psub getchar(str_$, ptr) char_$ = mid$(str_$, ptr, 1) endpsub char_$ psub divide(t, inputstr$) found=false if operandslist$(t) = "/" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value / second_value #print "Divide " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="/" //symbol found operandslist$(t)="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ #print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub multiply(t, inputstr$) found=false if operandslist$(t) = "*" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value * second_value #print "Multiply " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="*" //symbol found operandslist$(t) ="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub subtract(t, inputstr$) found=false if operandslist$(t) = "-" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value - second_value #print "subtract " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="-" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub add(t, inputstr$) found=false if operandslist$(t) = "+" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value + second_value #print "Add " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="+" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$
Spoiler
function makeintslist(inputstr$) dim list$(1) tokens =splittoarray(inputstr$, " +-=/*", list$(), 1 ) #print inputstr$ for t=1 to tokens #print list$(t) next t endfunction list$() function makeoperandlist(inputstr$) operandcount =0 dim newlist$(1) for tt=1 to len(inputstr$) char$ = getchar(inputstr$, tt) select char$ case "/", "*", "+", "-" inc operandcount redim newlist$(operandcount) newlist$(operandcount) = char$ #print char$ endselect next tt for tt=1 to operandcount //#print newlist$(tt) inc nothing next tt dim mylist$(operandcount) for t=1 to operandcount mylist$(t) = newlist$(t) next t endfunction mylist$() psub calculate(inputstr$) //dim intslist$(1) //dim operandslist$(1) //dim intslist(1) //remove white spaces inputstr$ = replace$(inputstr$, " ", "", 0, 0, 0) intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //first divide or multiply //Refresh ints list intsamount = getarrayelements(intslist$() ) redim intslist(intsamount) for t=1 to intsamount intslist(t) = val (intslist$(t) ) #print intslist(tt) next t for divmult=1 to getarrayelements( operandslist$() ) if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //Now we have our flag list //first count the remaining operands //I shouldn't need any of this now ==== keeping it for old time sake //dim newlist$(1) //for tt=1 to 7 //if operandslist$(tt) !="!" //inc operandcount //redim newlist$(operandcount) //newlist$(operandcount) = operandslist$(tt) //endif //next tt //dim newintlist$(1) //for tt=1 to getarrayelements(intslist$()) //if intslist$(tt) !="!" //inc intcount //redim newintlist$(intcount) //newintlist$(intcount) = intslist$(tt) //endif //next tt //======================keeping this in case i fuck up====================/// //so basically in this little block of code //We're resizing the actual int list based on the string int list //to line up with operands intsize =getarrayelements( intslist$() ) redim intslist( intsize ) for tt=1 to intsize intslist(tt) = val (intslist$(tt)) #print intslist(tt) next tt //for gg=1 to operandcount //perandslist$(gg) = newlist$(gg) //next gg //finally attempt solving operandcount = getarrayelements( operandslist$() ) for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) endpsub inputstr$Spoiler
; PROJECT : TestingAgain ; AUTHOR : Microsoft ; CREATED : 5/24/2016 ; EDITED : 5/25/2016 ; --------------------------------------------------------------------- //I don't want to write the functions so i'll define some of these things specifically inputstr$="1800-3/3+28*8/9-8/2" //inputstr$="1800-1+28*8/9-8/2" //inputstr$="1800-1+224/9-8/2" //inputstr$="1800-1+24-8/2" //inputstr$="1800-1+24-4" dim intslist(8) intslist(1)=1800 intslist(2)=3 intslist(3)=3 intslist(4)=28 intslist(5)=8 intslist(6)=9 intslist(7)=8 intslist(8)=2 dim intslist$(8) //make a list of the ints that are flagged for t=1 to 8 intslist$(t)=str$(intslist(t)) next t dim operandslist$(7) operandslist$(1)="-" operandslist$(2)="/" operandslist$(3)="+" operandslist$(4)="*" operandslist$(5)="/" operandslist$(6)="-" operandslist$(7)="/" intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //first divide or multiply for divmult=1 to 7 if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //Now we have our flag list //first count the remaining operands //I shouldn't need any of this now ==== keeping it for old time sake //dim newlist$(1) //for tt=1 to 7 //if operandslist$(tt) !="!" //inc operandcount //redim newlist$(operandcount) //newlist$(operandcount) = operandslist$(tt) //endif //next tt //dim newintlist$(1) //for tt=1 to getarrayelements(intslist$()) //if intslist$(tt) !="!" //inc intcount //redim newintlist$(intcount) //newintlist$(intcount) = intslist$(tt) //endif //next tt //======================keeping this in case i fuck up====================/// //so basically in this little block of code //We're resizing the actual int list based on the string int list //to line up with operands intsize =getarrayelements( intslist$() ) redim intslist( intsize ) for tt=1 to intsize intslist(tt) = val (intslist$(tt)) next tt //for gg=1 to operandcount //perandslist$(gg) = newlist$(gg) //next gg //finally attempt solving operandcount = getarrayelements( operandslist$() ) for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) print inputstr$ print "hi" print "Attempting to use above code now as a psub" //myvalue$ = calculate("5+5+5") //print myvalue$ //myvalue2$ = calculate("10+10+10") //print myvalue2$ myvalue3$ = calculate("30*30") print myvalue3$ myvalue4$ = calculate("1000/10+ 100 +10") print myvalue4$ waitkey waitnokey psub getchar(str_$, ptr) char_$ = mid$(str_$, ptr, 1) endpsub char_$ psub divide(t, inputstr$) found=false if operandslist$(t) = "/" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value / second_value #print "Divide " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="/" //symbol found operandslist$(t)="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ #print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub multiply(t, inputstr$) found=false if operandslist$(t) = "*" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value * second_value #print "Multiply " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="*" //symbol found operandslist$(t) ="!" startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //try to flag the integer list intslist$(t)="!" //flagged intslist$(t+1) = str$(result) //store this result too //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub subtract(t, inputstr$) found=false if operandslist$(t) = "-" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value - second_value #print "subtract " +str$(first_value ) +" "+ str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="-" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ psub add(t, inputstr$) found=false if operandslist$(t) = "+" first_value =intslist(t) second_value =intslist(t+1) firstvalue$ =str$(first_value) secondvalue$= str$(second_value) firstlength = len(firstvalue$) secondlength = len(secondvalue$) //try the divide and conquer!! result = first_value + second_value #print "Add " +str$(first_value ) +" " +str$(second_value) for gx=1 to len(inputstr$) //this part tries to find the symbol in the source string and replace it if getchar(inputstr$, gx) ="+" //symbol found startps = gx extractst = startps -firstlength endps = firstlength + secondlength+1 removed$ = mid$(inputstr$, extractst, endps ) //#print removed$ //#print result //Convert the result number to a string for injection into the source string solution$ = str$(result) intslist(t+1)= result //Update the ints list? //Inject a "!" instead of the sub string we just solved inputstr$ = replace$(inputstr$, removed$, "!", extractst-firstlength+secondlength, 0, 1) //only replace the first occurence //start at 0 //Inject the result inputstr$ = replace$(inputstr$, "!", solution$, extractst-firstlength+secondlength, 0, 1 ) bb =gx n$ =inputstr$ exitfor endif next gx endif endpsub n$ function makeintslist(inputstr$) dim list$(1) tokens =splittoarray(inputstr$, " +-=/*", list$(), 1 ) #print inputstr$ for t=1 to tokens #print list$(t) next t endfunction list$() function makeoperandlist(inputstr$) operandcount =0 dim newlist$(1) for tt=1 to len(inputstr$) char$ = getchar(inputstr$, tt) select char$ case "/", "*", "+", "-" inc operandcount redim newlist$(operandcount) newlist$(operandcount) = char$ #print char$ endselect next tt for tt=1 to operandcount //#print newlist$(tt) inc nothing next tt dim mylist$(operandcount) for t=1 to operandcount mylist$(t) = newlist$(t) next t endfunction mylist$() psub calculate(inputstr$) //dim intslist$(1) //dim operandslist$(1) //dim intslist(1) //remove white spaces inputstr$ = replace$(inputstr$, " ", "", 0, 0, 0) intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //first divide or multiply //Refresh ints list intsamount = getarrayelements(intslist$() ) redim intslist(intsamount) for t=1 to intsamount intslist(t) = val (intslist$(t) ) #print intslist(tt) next t for divmult=1 to getarrayelements( operandslist$() ) if operandslist$(divmult) ="/" then inputstr$ = divide(divmult, inputstr$) if operandslist$(divmult) ="*" then inputstr$ = multiply(divmult, inputstr$) next divmult intslist$() = makeintslist(inputstr$) operandslist$() = makeoperandlist(inputstr$) //Now we have our flag list //first count the remaining operands //I shouldn't need any of this now ==== keeping it for old time sake //dim newlist$(1) //for tt=1 to 7 //if operandslist$(tt) !="!" //inc operandcount //redim newlist$(operandcount) //newlist$(operandcount) = operandslist$(tt) //endif //next tt //dim newintlist$(1) //for tt=1 to getarrayelements(intslist$()) //if intslist$(tt) !="!" //inc intcount //redim newintlist$(intcount) //newintlist$(intcount) = intslist$(tt) //endif //next tt //======================keeping this in case i fuck up====================/// //so basically in this little block of code //We're resizing the actual int list based on the string int list //to line up with operands intsize =getarrayelements( intslist$() ) redim intslist( intsize ) for tt=1 to intsize intslist(tt) = val (intslist$(tt)) #print intslist(tt) next tt //for gg=1 to operandcount //perandslist$(gg) = newlist$(gg) //next gg //finally attempt solving operandcount = getarrayelements( operandslist$() ) for cc=1 to operandcount if operandslist$(cc) = "-" then inputstr$ = subtract(cc, inputstr$) #print inputstr$ if operandslist$(cc) = "+" then inputstr$ = add(cc, inputstr$) next cc //The values in the code above evaluate to : startps = //inputstr$ = replace$(inputstr$, mid$(inputstr$, 0, 5), "!", 0, 0, 1) endpsub inputstr$So will we have to use the play basic compiler to run this or are you making a stand alone exe?
So will we have to use the play basic compiler to run this or are you making a stand alone exe?Oh haha. Sorry I didn't see that post. It will be able to run on PC. That's right. Windows. It's an emulator and a dev tool. It may even have a step-through feature so you can step through the program and see where a bug occurs or get details on internal values/variables in that exact state of the program.
Update
I have created a basic arithmetic parser at last using all the previous things I knew. It wasn't easy. not at all.
But I did some really strong critical thinking and a few steps of trial and error and apparently I finally did the correct things.
So yeah now I have a simple math library that can solve basic arithmetic from an input string.
It can get tokens as well so I may also be able to use it for some of the code-level operations.
This is a huge step forward and it allows me to basically add math functions to expressions that involve or deal with variables.
TinySB is still a go and from this point on things just got a lot easier!
I'm willing to give away the source code or project file/s so if anyone gets curious or wants to see it let me know. One thing though, you'll have to have play basic set up to use the sources. This is a huge WIP and may not be done until this December at this rate. I don't work on it every day but speed is picking up rapidly now.
Update
I'm working on an extended version of the math parser which will work as the core tokenizer. The tokenizer is the step that occurs when an interpreted or compiled language program creates some kind of map or data set about the program that is easier to interprete than working on strings directly.
The lexer/parser then is able to step through this list or data set in a variety of ways to make sense of the program and re-format it into a way that can be executed either by a virtual machine or by a runtime interpreter or by a binary interpreter or machine code language directly.
TinySB will first be run as part of an interpreted language runtime internally. You shouldn't notice too much of a performance issue.
Hopefully what can happen is that the parser/lexer will create a functional list of the same code as the input code and then it can simply execute it line by line by expression evaluation. Hopefully doing it this way does not cause slowdowns but I can not be sure yet until I test it fully.
Once this step is fully completed and the tokenizer is finished I can rebuild some of the interpreter to better handle the expressions and I will have something akin to an executable expression evaluator machine. A little black-box if you will.
I'm still a big step away from actually having a programming language completed but I am pushing along.
If my upcoming math courses don't eat up all my brain power you can count on a public release pretty soon. It won't be much, probably able to just run hello world and such. Actually TINYSB can already run a basic hello world program ^_^
Commands that will be included in the upcoming release will be those I posted about in the already working post.
See below:
So yeah basically just gotta keep working on this and get it into a workable shape today and maybe some of tomorrow if things in my life don't get too weird.
Spoiler
dim variablename[dimensions] dim variablename[dimensions,dimensions] dim variablename[dimensions,dimensions,dimensions] variablename=value variablename$=value input$ print print variablename print variablename$ print variablename[dimensions] and so forth. BGPUT BGGET (hopefully bgget will work as expected) The arrow keys Up down left and right will serve as inputs. Input timing will not be just like in SmileBasic to start. Gcolor fully works (sort of) There will be more as well probably.Update
Let's hear it for evaluating whether or not the == operator exists within an expression that expected it (error checking)
I'm working on properly implementing the early version of the if statement right now, and creating a boolean expression evaluator that can also pull variable names during comparison ( == operations ) and find out the state of the parameters. Because I already coded simplemath expressions without parenthesis should be easy to resolve.
I'll also have to check the input types during this, and I've decided instead of labeling the tokens globally I'll label them on a per expression basis to better suit the situation which might mean stepping through the token list more than once but hey it's working. And it's fast
Update
I'm on a roll today but I already found one or two errors with this code, it's okay shh I'll fix it. :)
Here is the expression elevator to start with. It relies on the SimpleMath math parser I created.
SimpleMath parser also relies on all parenthesis math being resolved in an expression first (but that's okay I'll create something that does that later)
The code is here:
http://pastebin.com/tQnsCAFG
This function is quick n dirty and clean. It relies on quite a few other functionalities I already created.
Basically now, when I find an expression that starts with IF, as well as any = sign I can fire the whole tokenslist at this and get a true/false back.
For cases that involve singular statements like IF value I'll have a secondary check after the = sign which over rides the previous call.
What that will do is allow a checking for a boolean state.
If I'm evaluating and I run into a function name I'll simply have a secondary evaluate function parser for which I'll get the result and return types back and have that function run. For now i'm not going to worry about functions inside expressions using IF since it's very broad but there is a very simple way to do it.
The meat of the interpreter is now being worked on finally though now that the math parser is out of my way which I'm very happy about. :)
Also again... because of the way the math parser had to work it also solved the issue of tokenizing the lot of the code.
This feels like a heavy grind. Wish me luck!
Update
ok ok I'll stop posting so much but we have results.
'LITERAL' expression evaluation now works.
There's only two steps away from this.
The first step is to convert all non literal expressions for comparison operator into literal expressions by evaluating all of the contained expressions first.
This isn't as easy as it sounds but I can use a recursive method, Hopefully and then continue stepping through and putting tokens from the results onto a stack
to reformat the string without working on a string directly (The expressions themselves will be tokens seperated by I dont know yet )
Well here is the result of directly testing literal expression evaluation:
This should work pretty well for most other cases.
Now the good part, IF EXPR THEN -> Result should be able to execute soon.
Without variables there still isn't a lot you can do but i'll make basic (first level) variables accesible asap so that TinySB is at least somewhat useful.
Printing of strings will be supported too as well as assignment and if I can finish those few tasks today I can release a very unstable Alpha version soon.
Update
Alright I promised I'd stop posting so many updates for a while and what a while has it been.
Interestingly enough not too MUCH has changed.
Except then again, a lot has.
So first of all I've separated entirely the concept between simple math (the math stack evaluator) and the tokenizer.
I have a tokenizer that can now differentiate using a simple state machine whether or not a token is a variable an operand or something entirely different.
It can fully separate an expression into variables, keywords, operands (of my choosing), and literal numbers. Including parenthesis.
Although I may have a special case later to check whether I've run into a function or not (or a keyword with parameters) when I see parenthesis.
That will depend more on the first keyword found.
What else?
Well, I am one step away from a secondary math stack resolver.
What does this mean? It means that something inside TinySB is now able to seperate everything into tokens, and then get the literal values of a variable and inject them back into the token list. It's then able to take those and squish them even more together, forming essentially tokens that represent full mathematical expressions with only whole numbers.
These tokens are going to have a special label called "expression".
In other words I've summarized TinySb's tokens into a few things so far and am now using token labels for the parser/lexer.
This is only a component of the development though it's not very functional in whole on it's own.
The reason i'm tackling this issue is so that I can solve the higher level issues of TinySB next.
Why do I call them issues? Well because they are problems that I have to face in order to gain function to a means.
Here's a screenshot (finally) of my tokenizer /interpreter making sense of tokens on the stack:
Essentially I have reduced processing input yet another step.
Now in one fell step I can basically label everything about an input line.
This is beyond cool (for me).
UPDATE
This is rare, 2 updates in a day.
I have successfully implemented the VERY first proper variable value assignment.
no joke. I feel amazing.
I didn't think I would get this far so soon.
Well! here it is , spoiler below:
This means that on a function level (the full readline thing isn't done yet)
Users of TinySB will now be able to do this
put("Myvariable=10")
put("Myvariable2=Myvariable+10")
This may not seem huge but it kind of is.
It basically is one step closer to making TinySB a working expression evaluator. It is not yet a full coding language though.
But being able to evaluate expressions (and actually solve the math) is important.
It's even possible now to do this
put("Myvariable=25+15+10/2")
I have more testing to do but it should resolve a correct answer.
Note that those put commands have to be hard coded into PlayBasic for the time being but
at this juncture I may as well set up the first program loader.
It will load a program in from text and allow use.
TinySB still isn't super useful YET but it is definitely clunking along and picking up momentum now that i have solved BOTH the math parser
and some of the regular expression issues.
It doesn't even use a formal BNF which is impressive as heck but later I may implement a BNF layer or a functional linguistics layer.
REJOICE! TinySB lives and is picking up progress fast.
Spoiler
UPDATE
FULL variable assignment now working in TinySB! This is a BIG deal.
Here is the final update probably for tonight. Tested and true... in all it's beauty it can process variables and add subtract divide and multiply them, it also allows defining new variables by way of the assignment operator as you'd expect AND it can process mixed variables operators (math) and numbers.
This is an important step forward in TinySB's progress and the first time that the project has been functional beyond BG layers and graphics. and text.
It may soon be possible to create a complete program with TinySB which can conditionally jump.
here's the screenshot:
Spoiler
Update
Tonight I'm about to work on the function layer and get something actually working within it.
Will report on it when finished.
After that, I'm going to have a look through SmileBasic's command list and look for all commands which just take numeric parameters.
All the ones that do will be parsed out over time to be included and supported but math for them won't be supported yet.
I'll have to parse each parameter as an expression and see if it contains deeper expressions. Overall though
it will work on a basic level and allow more SB functionality by the end of the month.
By the end of feburary I am hoping to have finished a large portion of SmileBasics command set without supporting recursive function calls in expressions... however; if I can manage to pull it off it'll support finite depths of expression calls within expression calls.
Here's an example of the kind of code I need to support in TinySB and the current "big" problem.
DEF Myfunction(A, B) OUT C A=A*A+(C-13) END GCOLOR Myfunction(255/3, MyFunction(19+M, 255-L) ), 18, 18In this specific case to parse that there's a few steps required. The first is to recognize GCOLOR (that's trivial) The next is the way in which the code is broken down. Starting from left to right I need the entirety of the expression before the, followed by the other two parameters 18 and 18 as well. The resulting token list WOULD look like this: Tokens$(1)="Myfunction(255/3, MyFunction(19+M, 255-L) ) Tokens$(2)="18" Tokens$(3)="18" in programming terms it means that I have to step through each parameter. Then parse each parameter. IF I happen to find a function call or another command, I need to recognize THAT command and then break temporarily, parse the parameters of that command then return, and get the result. Then I have to continue parsing the whole rest of the function call. In the case above I basically will end up having to branch twice to deal with the parameter of TWO functions. The innermost function first. Then I'll treat that function and all it's parameters AS a parameter of the outermost function. Then i have to deal with the outermost function and simulate it running. Once i've simulated it running I have to get the results. AFTER that, I can return to dealing with the fact it's a GCOLOR command and I can inject the results (all 3 of them) into the R G B values respectively. Then, finally. I can set the global ink color to those values!!! WHEW! See, parsing commands seems simple when you only allow real numbers. If that's not enough, I also have to break some of those parameters up and send them through the simple math function. If variables are involved then I have to actually convert them all to real numbers first and then send the whole string to simple math meaning I have to also identify where the math itself starts and ends within the total length of the target expression string. While I can still seperate everything into symbols of any label I choose it's still not the easiest task in the world. Wish me luck world.
Update
I'm almost done solving the function layer stack in TinySB. There's a few small problems with it but I have a very strong visual model of what's going to be going on with the function stack and function layer after taking my time to understand how it's done on traditional machines.
As a result the function layer when completed will be stable very early on into TinySB's life cycle.
Stable as in, I probably won't even have to touch or bother with the function layer for a very long time after this.
There's been talk of different ways to build something just like TinySB in another language for a few days now in SBS chat.
Today I've settled on a solution that one other person in the community agrees on I just have to run it by him again.
This new port will not be TinySB, and it will be a generic set of functions and such compatible with SmileBasic's native formats.
Early support of binary writing for dat files and other filetypes will be included as early as possible (even though writing the dat header was a giant pain in the butt)
Additionally, I've found a combined set of libraries that allows sound and graphics and yes don't be surprised it's an off-shot of SDL which includes literally SDL itself.
This is the only real option in C#.
We're going to look into possibilities of more than one platform running this version of the project.
TinySB's development will continue as is so the new project will be a mirror of TinySB with a few differences.
One big difference is that we are going to be developing libraries which will represent programmatically the same things that we think SmileBasic itself does.
This is a pretty big step actually, a leap if you will. A lot more is possible with more people getting involved.
The project will be hosted on my github account (and also probably mirrored by other users too). The early template will be available for anyone interested but it will not do much it will just be a standard template project ready with all the required dll files etc.
Lastly.. progress on THIS project which I am tempted to call SmileBasic#, will be a lot faster than TinySB since many problems that were solved in TinySB will be trivial for me to solve a second time in another language.
Some other good news, SimpleMath is actually being ported to C# but we shouldn't need to run a VM at all with the new system that I have in mind.
Without needing to design a full vm progress will happen faster but it will require some hand-porting.
I don't know how to call a compiler/linker for C# indirectly..
Whether we go full VM on this or just a 1:1 translate I'm not sure of yet but it's looking like a 1:1 translation.
That means the end project will consist of sets of libraries to wrap smilebasic functionality, and a program which converts the smilebasic code into code the wrapper library understands, and then possibly a make file that automatically chains the project through command line or something into a linked .net exe file a person can click and execute.
Pretty cool technology if we get this working.
Happy coding!
I'm super excited for this! c:
Will we essentially be able to make games and programs on our computers with the software you're developing? And it'll be practically the same as SmileBasic's language, so I wouldn't have to learn another language to begin programming?
If we can do that, then I will definitely be using this software! I'm not a very advanced user on here, but I do know how to do simple things on SmileBasic! I usually develop games quickly by making code generators! If you can make the functionality to where I can use multiple slots like SmileBasic does, I'll be very happy.
And if I can use this to make games for Steam Greenlight, that'll be even better! :D