Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
_IIF limits two questions
#11
I'm definitely grooving on the new _IIF command! So easy and concise.  Smile

IF a = 5 then b = 10 else b = 5 becomes b = _IIF(a=5, 10, 5). What's not to like?! Thanks, dev team.
Reply
#12
I just recently upgraded to the newest version. I have to say I like _IIF as well.

It nests well too as a function from my recent guitar fret board ap demonstrates:

FUNCTION NoteName$ (n AS tone)

    'IF n.ac THEN '                                              If note enharmonic
    '    IF Vtog%(shrp_flt) THEN '                              If in flat mode
    '        NoteName$ = n.bf
    '    ELSE '                                                  If in sharp mode
    '        NoteName$ = n.bs
    '    END IF
    'ELSE '                                                      If note NOT enharmonic
    '    NoteName$ = n.nt
    'END IF

    NoteName$ = _IIF(n.ac, _IIF(Vtog%(shrp_flt), n.bf, n.bs), n.nt)

END FUNCTION 'NoteName$

Nine lines of a compound IF...THEN block distilled down to one is not too shabby.
DO: LOOP: DO: LOOP
sha_na_na_na_na_na_na_na_na_na:
Reply
#13
Yes, it's nice. The best part is that it's short-circuiting, so you may get a small performance boost depending on your use case.

That said, I wouldn't overuse it. Excessive use or deep nesting of _IIF can lead to code that's harder to read and maintain.
Reply
#14
(05-13-2025, 10:51 PM)a740g Wrote: Yes, it's nice. The best part is that it's short-circuiting, so you may get a small performance boost depending on your use case.

That said, I wouldn't overuse it. Excessive use or deep nesting of _IIF can lead to code that's harder to read and maintain.
Agreed, I can see where it can get pretty confusing. Part of my coding schtick is to see how small I can write my code, and I've done some incredibly convoluted, multi-line, branchless boolean expressions in that pursuit. The _IIF command at least allows me to dispense with the possibility of making sign errors that loomed large in doing the branchless stuff.
DO: LOOP: DO: LOOP
sha_na_na_na_na_na_na_na_na_na:
Reply
#15
I'm well acquainted with nested IIFs, particularly in Excel formulas! LOL! 
(The formula version is "IF", but VBA macros use the familiar IIF spelling.)

Luckily, Excel allows you to add linebreaks and indenting, albeit manually, to your formulas, to help keep track of what's happening, and even preserves this formatting. 

Should you find yourself in a similar situation in QB64PE (i.e., trying to debug someone else's nested _IIF code, not your own code, because you won't be abusing _IIF that way! LoL), you can probably use a similar method using the line continuation character "_" to help make things more readable.
Reply
#16
Honestly, I like this old code better than the _IIF statement:

    'IF n.ac THEN '                                              If note enharmonic
    '    IF Vtog%(shrp_flt) THEN '                              If in flat mode
    '        NoteName$ = n.bf
    '    ELSE '                                                  If in sharp mode
    '        NoteName$ = n.bs
    '    END IF
    'ELSE '                                                      If note NOT enharmonic
    '    NoteName$ = n.nt
    'END IF

Things are spread out on multiple lines and each segment is commented to help understand what it's supposed to be doing.  I'd personally find the above much easier to maintain and work with after a 6 month break, where I might find myself having to go back and rework the code for some error or new enhancement, than I would the _IFF alternative.

NoteName$ = _IIF(n.ac, _IIF(Vtog%(shrp_flt), n.bf, n.bs), n.nt)

There's a lot less code there for you to write and work with, but also a lot less explanation of what's going on with that code.  It's just user defined types which you might not remember what every element stands for in the future, and arrays and indexes, and... a huge question mark which says, "WTF WAS THIS DOING?!!"

It may save you a few bytes disk space and compact the code down a byte or two, but you have to consider if it's going to be worth the hit to readability and maintenance with the future of the code.  Over the years, I've thrown together a LOT of quick and sloppy code, and been proud of it at the time, only to have to almost rewrite the whole thing from scratch a couple years later just because I couldn't figure out my own damn flow and logic with stuff.  LOL!

My opinion with _IFF is that it's convenient, but it's a tool that I'd personally tend to use for fairly obvious stuff which isn't hard to decipher and doesn't need any comments to sort out.  It's something I personally find just too murky to understand for complex stuff.   If you need comments, in my opinion, it's probably best to use an IF structure and lay out those comments at the various blocks as you've did with the original code.

Your future self will thank you.  Big Grin  At least, mine usually does.  Wink
Reply
#17
I agree with you on the complex stuff. There are lots of places where _IIF works to simplify things, mainly in constructing strings and as a way to neatly wrap up logic. Here are a few examples:

Code: (Select All)
sItemList = sItemList + _IIF(Len(sItemList) = 0, "", ",") + NextItem$

arrKeys(c_bKey_CrsrUp) = _IIF(_BUTTON(c_bKey_CrsrUp) = 0, FALSE, TRUE)

PRINT "GetColorDictionary%(arrColorValue()) RETURNS " + _IIF(bResult, "TRUE", "FALSE")

iErrorCount = iErrorCount + _IIF(SaveLongDictionaryCaseSensitive%(arrLongDict(), "1", cRed&), 0, 1)

GetColorDictionary% = _IIF(iErrorCount = 0, TRUE, FALSE)

sValue = _IIF(m_arrControlMap(iPlayer, iWhichInput).repeat, "Y", "N")

PRINT LEFT$(cstr$(_IIF(GetBit%(iNum%, iLoop), iValue, 0)) + "   ", 3)

GetBit% = _IIF(MyValue% = MyValue% AND BitValue%, TRUE, FALSE)

sChanged = sChanged + _IIF(Len(sChanged) = 0, "", Chr$(10)) + "    " + sLine

sNext = sNext + _IIF(HasBit%(iByte, iBit), "1", "0")

json_IsLargeNumber = _IIF(InStr(json_Value, "."), Len(json_Value) >= 17, Len(json_Value) >= 16)

sText = sText + _IIF(iLastKeyDown > 0, VirtualKeyCodeToString$(iLastKeyDown) + " (" + _Trim$(Str$(iLastKeyDown)) + ")", "")

sText = sText + _IIF(arrMouse(iIndex).LeftDown, "1", " ")
sText = sText + _IIF(arrMouse(iIndex).MiddleDown, "2", " ")
sText = sText + _IIF(arrMouse(iIndex).RightDown, "3", " ")

IsWeapon% = _IIF(iPos > 0, TRUE, FALSE)
IsArmor% = _IIF(iPos > 0, TRUE, FALSE)

Print "chars missing : " + _IIF(Len(missing$) = 0, "(none)", Chr$(34) + chars$ + Chr$(34))

Print "Rotated by " + cstr$(D) + " degrees" + _IIF(iMissing = 0, "", " (" + cstr$(iMissing) + " points missing)") + ":"

' an example of a nested IIF (only one level!):
Print _IIF(pDir% = cRight, "cRight", _IIF(pDir% = cLeft, "cLeft", "?")) + "      ";

sMessage = sMessage + _IIF(Len(sMessage) = 0, "", " AND ") + cstr$(iPlayerLoop + 1)

sTest = "_DEFAULTCOLOR " + _IIF(_DEFAULTCOLOR = arrColor(iLoop1).value, "=", "!=") + " fgcolor" + _

sValue = _IIF(m_arrControlMap(iPlayer, iWhichInput).repeat, "Y", "N")

sLine = sLine + _IIF (iLoopX > 1, chr$(9), "") + cstr$(pixelColor&)

sLine = sLine + _IIF(pixelColor& = 0, ".", "#")

print "iWarningCount=" + cstr$(iWarningCount) + _IIF(bDoCount, " <- COUNTDOWN TO BOOM!", "")

bValue = _IIF(m_iRoundsPerGame = 0, TRUE, FALSE)

PrintString 10, 18, _IIF(bValue, "Infinite", cstr$(m_iRoundsPerGame))

sMessage = _IIF(m_arrShip(iShip1).Left_IsPressed, "LEFT ", "") ' + etc etc

sMessage = sMessage + _IIF(Len(sMessage) = 0, "", " AND ") + cstr$(iPlayerLoop + 1)

Locate m_iInstrStartRow+6, m_iInstrStartCol: Print "[    / ]   TOGGLES MOVEMENT      = " + _IIF(m_arrPlayer(1).IsMoving, "TRUE", "FALSE")

Locate m_iInstrStartRow+7, m_iInstrStartCol: Print "INS  / DEL TOGGLES REPEAT KEYS   = " + _IIF(bEnableRepeatingKeys, "TRUE", "FALSE")

Color TextColor, cEmpty: Locate iLine, 36: Print Left$(_IIf(ChromaKeyEnabled, "ON", "OFF") + "    ", 4);

mem50 = _IIF(Sgn(mem53) = -1, 128, 0)

getBit = _IIF((Value And (2 ^ BitNo)) = 0, 0, 1)

pg! = Abs(bDiff&) / Abs(gDiff&) * _IIf(g1& < g2&, 1, -1)
Reply
#18
Nested _IIF functions can get hard to read.

I would rewrite 
Code: (Select All)
NoteName$ = _IIF(n.ac, _IIF(Vtog%(shrp_flt), n.bf, n.bs), n.nt)
As

Code: (Select All)
NoteName$ = _IIF( n.ac,                                 _
                  _IIF( Vtog%( shrp_flt ), n.bf, n.bs), _
                  n.nt )
That said, I still prefer nested _IFF's than nested IF-THEN-ELSE structure because:

The IF-THEN-ELSE structure really requires me to read the whole thing to figure out what it is doing.

The single assignment statement with nested _IIF's: I know as soon as I read "NoteName$ =" that I'm dealing with an assignment statement that will assign some value to NoteName$.  I find that helps me avoid playing less of the game of "What is Waldo doing?"  (i.e. it is immediately clear what the code is doing without needing any comments to tell me what the code is doing, which is awesome because not needing the comment reduces sensory overload via the game of "Where's Waldo".  Yeah, I don't have much love for Waldo ...)
Reply
#19
(05-14-2025, 12:56 PM)CharlieJV Wrote: Nested _IIF functions can get hard to read.
I would rewrite 

Exactly my point - in QB64PE, as with Excel, you can simply format it better to make it readable.
(The same is true for any command, not just IIF. I see a ton of code posted on here with multiple commands on one line done for convenience, where a simple line break + indenting makes it a lot easier to follow.)

(05-14-2025, 12:56 PM)CharlieJV Wrote: That said, I still prefer nested _IFF's than nested IF-THEN-ELSE structure because:

The IF-THEN-ELSE structure really requires me to read the whole thing to figure out what it is doing.

The single assignment statement with nested _IIF's: I know as soon as I read "NoteName$ =" that I'm dealing with an assignment statement that will assign some value to NoteName$. 

I've found the same thing - using IIF to neatly wrap up logic makes code easier to understand.

(05-14-2025, 12:56 PM)CharlieJV Wrote: Yeah, I don't have much love for Waldo ...)

Sit down, Waldo!
Tongue
Poor Waldo!
LoL
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  What limits you? Unseen Machine 9 986 09-05-2025, 01:32 AM
Last Post: madscijr
  Half baked pipe dream questions - hardware and os Parkland 9 1,312 05-23-2025, 03:00 PM
Last Post: madscijr
  IDE suggestions / editor questions madscijr 14 2,340 05-01-2025, 12:56 PM
Last Post: madscijr
  Questions about INSTR Circlotron 7 1,022 04-27-2025, 03:12 PM
Last Post: mdijkens
  Just a Few Questions TarotRedhand 15 2,858 09-11-2023, 12:10 PM
Last Post: DSMan195276

Forum Jump:


Users browsing this thread: 2 Guest(s)