Page 3 of 3

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 2:36 am
by mesozorn
Kaeru Gaman wrote:why 1- and Not, when you have the And..?
Because try this...

Code: Select all

z=(1 And (5.5>5.3))
Debug z
...and you'll see why I don't use it by itself. It works for variables but I prefer a version that works for everything imaginable, including literals. This way:

Code: Select all

z=(1-(1 And Not(5.5>5.6)))
Debug z
z=(1-(1 And Not(5.5>5.3)))
Debug z
...works for both/all contingencies.

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 2:59 am
by mesozorn
idle wrote:or this and is probably quicker than a not

Code: Select all

Macro IIFn(expr,y,n)
IIFEvaln((1 And(expr)),y,n)
EndMacro

Macro IIF(expr,y,n)
IIFEval((1 And(expr)),y,n)
EndMacro
LOL... that was my original, original version months ago, and its failure to properly handle literal floats like (5.5>5.3) as expressions is what led me down the whole Val(Str()) path in the first place. It's true that the above will work for the majority of situations, but not all of them, unlike the two versions we arrived at earlier today.

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 5:36 am
by idle
it works for floats but it won't return them

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 6:53 am
by mesozorn
idle wrote:it works for floats but it won't return them
Er.. what do you mean exactly?

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 8:01 am
by idle
improved the string speed but you need to pass the address of the string
just call the macro with the return types you want

edit bloddy dyslexia!

edit to NOT as (1 And 5.5 = 5.6) dosen't work

iFFI , iFFF, IFFD, IFFQ, IFFS

Code: Select all

Procedure.s IIFEvals(expr,*y,*n)
If expr
 ProcedureReturn PeekS(*y)
Else
 ProcedureReturn PeekS(*n)
EndIf
EndProcedure

Procedure IIFEvali(expr,y,n)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure.f IIFEvalf(expr,y.f,n.f)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure.d IIFEvald(expr,y.d,n.d)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure IIFEvalq(expr,y.q,n.q)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Macro IFFI(expr,y,n)
IIFEvali((Not(expr)),n,y)
EndMacro

Macro IFFF(expr,y,n)
IIFEvalf((Not(expr)),n,y)
EndMacro

Macro IFFD(expr,y,n)
IIFEvald((Not(expr)),n,y)
EndMacro

Macro IFFQ(expr,y,n)
IIFEvalf((Not(expr)),n,y)
EndMacro

Macro IFFS(expr,y,n)
IIFEvals((Not(expr)),n,y)
EndMacro

Macro IFFfn(expr,a,b)
 If expr : a : Else : b : EndIf  
EndMacro 

Procedure p2(a.s)
  MessageRequester("test",a)
EndProcedure
  

a=5
b=4
c=2
d=3
e.f = 5.6
f.f = 5.5 

IFFfn(5>4,p2("hello"),MessageRequester("test","no"))
Debug IFFS(5.5>5.4,@"yes",@"no")
Debug IFFI(a > b,200,100) 
Debug IFFF(e > f,200.1234567,100.1234567)
Debug IFFD(5.5 = 5.6,200.123456789012345,10.123456789012345)
Debug IFFQ(a > c,$FFFFFFFF,$EEEEEEEE)


lp = 1000000
st = GetTickCount_()
For a = 1 To lp
   x$ = iFFs(5.5 > 7.5,@"200",@"100")
Next   
et1.f = (GetTickCount_() - st) / lp
st = GetTickCount_()
For a = 1 To lp
   If 5.5 > 7.5
      x$ = "200"
   Else
      x$ = "100"     
   EndIf
Next     
et2.f = (GetTickCount_() - st) / lp


MessageRequester("test", "IFFs " + StrF(et1,6) + " if " + StrF(et2,6))

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 8:10 am
by mesozorn
idle wrote:improved the string speed but you need to pass the address of the string
just call the macro with the return types you want
It still doesn't handle literal floats correctly though with only (1 and expr). Uncomment and change your line to:

Code: Select all

Debug IIFD(5.5=5.6,200.123456789012345,10.123456789012345)
Debug IIFS(5.5>5.7,@"yes",@"no")
...and note that it still returns the "yes" result both times, even though 5.5 doesn't equal 5.6 in the first example, and 5.5 isn't greater than 5.7 in the second.

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 8:19 am
by idle
ohh crap! yes you are right :lol:

changed it back to not

Re: IIF functionality made simple

Posted: Tue Nov 10, 2009 8:26 am
by mesozorn
idle wrote:ohh crap! yes you are right :lol:
Hehe... for those ones it seems we still can't get away from using one of the two methods discovered earlier to handle them accurately. Either just the Not by itself or the "barbarous abomination" (1-(1 And Not(expr))).

I still don't know why only the barbarous one returns correctly in all cases (straight variable value assign debug) while the Not one by itself only works in the procedure but not independently. Odd quirk.

Re: IIF functionality made simple

Posted: Wed Nov 11, 2009 4:10 am
by idle
I don't know anymore I'm so confused. :lol:
It appears to be around a 2x speed penalty in all cases so it's a pretty good improvement.

Code: Select all

 
Procedure.s IIFEvals(expr,*y,*n)
If expr
   ProcedureReturn PeekS(*y)
Else
   ProcedureReturn PeekS(*n)
EndIf
EndProcedure

Procedure.i IIFEvali(expr,y,n)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure.f IIFEvalf(expr,y.f,n.f)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure.d IIFEvald(expr,y.d,n.d)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Procedure.q IIFEvalq(expr,y.q,n.q)
If expr
  ProcedureReturn y
Else
  ProcedureReturn n
EndIf
EndProcedure

Macro IIFI(expr,y,n)
IIFEvali((Not(expr)),n,y)
EndMacro

Macro IIFF(expr,y,n)
IIFEvalf((Not(expr)),n,y)
EndMacro

Macro IIFD(expr,y,n)
IIFEvald((Not(expr)),n,y)
EndMacro

Macro IIFQ(expr,y,n)
IIFEvalf((Not(expr)),n,y)
EndMacro

Macro IIFS(expr,y,n)
IIFEvals((Not(expr)),n,y)
EndMacro

Macro IIFfn(expr,a,b)
If expr : a : Else : b : EndIf 
EndMacro 

;================================

Procedure p1(a.s)
   MessageRequester("P1",a)
EndProcedure
Procedure p2(a.s)
 result =  MessageRequester("P2",a,#PB_MessageRequester_YesNo)
 If result = #PB_MessageRequester_Yes
   ProcedureReturn 1 
 Else 
   ProcedureReturn 0
 EndIf      
EndProcedure

a=5
b=4
c=2
d=3
e.f = 5.6
f.f = 5.5
                            
Debug IIFS(5.4 = 5.4,@"yes",@"no") ;string return 
                  
Debug IIFI(a > b,200,100) ;Integer return  
         
Debug IIFF(e > f,200.1234567,100.1234567) ;float return 
        
Debug IIFD(5.5 = 5.6,200.123456789012345,10.123456789012345) ;Double return 
        
Debug IIFQ(a > c,$FFFFFFFFF,$EEEEEEEE) ;quad return 

;function call a regular macro with no return    
IIFfn(a>b And c>d,p1("true"),p1("false"))

; iif as a parameter in a function expecting a string calling a function with the result from the input 
p1(iifs(p2("Click Yes or Cancel"),@"You Clicked Ok",@"You Clicked Cancel"))

;iif getting the result of a function 
If CreateFile(0, "MacroTest.txt")
CloseFile(0)
Debug "Delete File : " + IIFs(DeleteFile("MacroTest.txt"),@"Yes",@"No")
EndIf


Re: IIF functionality made simple

Posted: Mon Apr 26, 2010 7:05 am
by avatar
This is my version of string handling in IIF

Code: Select all

Procedure.s IIFEvalss(expr,y.s,n.s)
  If expr
     ProcedureReturn y
  Else
     ProcedureReturn n
  EndIf
EndProcedure
Macro IIFSS(expr,y,n)
  IIFEvalss((Not(expr)),n,y)
EndMacro

Debug iifss(1=0,"TRUE","FALSE")
Debug iifss(1=1,"TRUE","FALSE")