Oxygen Basic
Programming => Problems & Solutions => Topic started by: Aurel on July 02, 2017, 11:24:50 AM
-
Hio Charles
sorry but i must bothering you about this problem.
sorry again if is fixed in new version...blame on me :D
i just try in one example :
string func
float res,result
select func
case "SIN" : result =sin(res)
case ....
case ....
end select
so in this case SELECT not respond on string varible func
BUT if i use
if func = "SIN" ....... then work
i just hope that this would be fixed
or i will (must ) replace func with integer
like fun
int fun
select fun
once again if this is solved in last version
all best Aurel :)
-
Hi Aurel,
Like C. the oxygen case is a low-level construct that does not support string comparisons. Cases translate directly into assembler. So you will have to use if..elseif..endif
-
So you will have to use if..elseif..endif
Script BASIC doesn't have a SELECT/CASE which I find restrictive in most BASIC languages. I've created some fairly large IF/ELSE IF/ELSE/END IF structures with complex expressions I could never do with a common CASE.
-
Case blocks are very fast in compiled languages. You can still use them for filtering:
string func
float res,result
select asc func
case "S"
if func="SIN" then
result =sin(res)
elseif func="SQR" then
result =sqr(res)
end if
...
case "T"
case ....
end select
-
Case blocks are very fast in compiled languages
Yes Charles ..and that is why I ask
thanks for suggestion...
my next idea would be ..maybe i can use string pointer casting ?
-
I expected that method with string pointer casting work
but not exactly because no mather what is s, only first case is selected
:'(
here is one way:
'string casting -> select/filtering
string s="SIN"
'(p AS string pointer)
p = cast (string)s
select p
case strptr "SIN"
print "OK..func(SIN)"
case strptr "TAN"
print "OK..func(TAN)"
end select
Ok it seems that best option would be to have strings
signed with numbers then use SELECT
like
fun_sin = 1
fun_cos = 2
fun_tan=3
then select
select fun
case 1
print fun_sin: sin(res)
Ok i will see.... ;)
-
If you convert your 3 or 4 character keywords into integers, you can use them in a case block like this:
int*p=strptr func
'THIS WILL WORK FOR 3 OR 4 CHAR KEYWORDS
string func="SQR"
float res=2, result
int*p=strptr func
select p
case "SIN" : result=sin(res)
case "SQR" : result=sqr(res)
end select
print result '1.41...
-
Hi Charles
I forgot for this way ::)
that is great and i tested more than 3-4 chars ..18 chars
and WORK ! :D
'THIS WILL WORK FOR 3 OR 4 CHAR KEYWORDS
string func
func="OxygenBasicSqrRoot"
'func="SIN"
float res=2, result
int *p = strptr func
select p
case "SIN"
result=sin(res)
case "OxygenBasicSqrRoot"
result=sqr(res)
case else
print "unknown func?"
end select
print result '1.41...
.
-
Careful! Only the first 4 characters are tested, as an integer
-
Charles
May i ask why CAST not work as *p = strptr s ?
and what is a main difference...
this thematic is not explained well and can be used in many string processing programs ,right?
-
Charles
I just tried with Djpeter ( from FB forum) math solver
and seems that your method work fine :D
you may try :
' simple expression solver FB DJPeters
'Oxygen basic version by Aurel
declare sub Unary (byref Result as float)
declare sub Parenthesized(byref Result as float)
declare sub Exponent (byref Result as float)
declare sub MulDiv (byref Result as float)
declare sub AddSub (byref result as float)
'declare sub DoUnary (Op as string,byref Result as double)
declare sub GetToken()
declare function IsDigit() as int
declare function IsAlpha() as int
declare function IsWhite() as int
declare function IsDelimiter() as int
declare function isFunction() as int
'enum TokenTypes / integer constant
% EOL = 1
% DELIMETER = 2
% NUMBER = 3
% IDENT = 4
'end enum
string Expression,Token,ch
int TokenType,cPos,TRUE=1,FALSE=0
sub sError(sErr as string)
print "Error: " & sErr
'beep:sleep:end
end sub
'---------------------------------
function IsDigit() as int
int c: c=asc(ch)
if c>47 and c<58 or c=46
return TRUE
end if
return FALSE
end function
'--------------------------------
function IsAlpha() as int
int c: c=asc(ucase(ch))
if c>64 and c<91
return TRUE
end if
return FALSE
end function
'---------------------------------
function IsWhite() as int
int c : c=asc(ch)
return ((c=32) or (c=9))
end function
'---------------------------------
function IsDelimeter() as int
int c: c=asc(ch)
if c=9 then return TRUE
c=instr("+-*/^()",ch)
if c>0 then return TRUE
return FALSE
end function
'---------------------------------------
function IsFunction() as int
int *f = strptr token
Select f
case "SIN"
return TRUE
case "COS"
return TRUE
case "TAN"
return TRUE
case "SQR"
return TRUE
end select
return FALSE
end function
'----------------------------------------
sub GetChar
cPos=cPos+1
if cPos>len(Expression) then
ch="":return
end if
ch = mid(Expression,cPos,1)
end sub
'---------------------------------------
sub GetToken()
GetChar()
if Ch="" then
Token = ""
TokenType = EOL
return
end if
if IsDelimeter()= TRUE then
Token = Ch
TokenType = DELIMETER
return
end if
if IsDigit()= TRUE then
Token = ""
while IsDelimeter()=FALSE and Ch<>""
Token=Token+Ch
GetChar()
wend
TokenType = NUMBER
cPos=cPos-1
return
end if
if IsAlpha() = TRUE then
Token = ""
while IsAlpha()=TRUE and Ch<>""
Token = Token + Ch
GetChar()
wend
'print "TOKEN:" & token
Token= UCASE(Token)
TokenType = IDENT
cPos=cPos-1
return
end if
end sub
'---------------------------------------------
sub AddSub(byref Result as float)
string Op
float Temp
Unary(result)
Op=Token
while Op = "+" or Op = "-"
GetToken()
Unary(Temp)
if Op="+" then
Result=Result+Temp
end if
if Op="-"
Result=Result-Temp
end if
Op = Token
wend
end sub
sub Unary(byref Result as float)
string Op
if TokenType=DELIMETER and (Token="+" or Token="-")
Op = Token
GetToken()
end if
MulDiv(Result)
if Op="-" then Result = -Result
end sub
sub MulDiv(byref Result as float)
string Op
float Temp
Exponent(Result)
Op=Token
while Op = "*" or Op = "/"
GetToken()
Exponent(Temp)
if op="*" then
Result *= Temp
else
if (Temp=0) then
sError("division by zero")
else
Result = Result / Temp
end if
end if
Op = Token
wend
end sub
sub Exponent(byref Result as float)
float Temp
Parenthesized(Result)
if (Token="^") then
GetToken()
Parenthesized(Temp)
Result ^= Temp
end if
end sub
sub Parenthesized(byref Result as float)
if token = "-" or token = "+" then Unary(Result)
if (Token ="(") and (TokenType = DELIMETER) then
GetToken()
AddSub(Result)
if (Token <> ")") then serror("unbalanced round brackets")
GetToken()
else
select TokenType
case NUMBER
Result = val(Token)
GetToken()
case IDENT
if IsFunction()= TRUE then
string Func : Func = Token
int *p = strPtr Func
float res : res = result
GetToken()
Parenthesized(res)
select p
' case "ABS": result = abs(res)
' case "ATN": result = atn(res)
case "COS": result = cos(res)
'case "EXP": result = exp(res)
'case "FIX": result = fix(res)
'case "INT": result = int(res)
'case "LOG": result = log(res)
'case "SGN": result = sgn(res)
case "SIN": result = sin(res)
case "SQR": result = sqr(res)
case "TAN": result = tan(res)
end select
else
serror("unknow ident / function " & Token)
end if
end select
end if
end sub
function Eval(byval s as string) as float
float result
Expression=s
cPos=0
GetToken()
AddSub(result)
return result
end function
string e
e = "sin(2+3)"
print e & " = " & Eval(e)
.
-
Hi Aurel,
Cast is just a way of fooling the compiler into accepting onions as apples :)