Your Digital Media Has Never Looked So Good

 
User avatar
Komag
Topic Author
Posts: 808
Joined: Fri Aug 22, 2014 3:42 am

How to skip an iteration in a FOR loop?

Sun Jun 02, 2019 7:47 pm

FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR EACH fruit IN testA
      testInt++
      IF TYPE(fruit) = "roString" THEN ? fruit ELSE testA.Next()
      ? "testNext() did one step, fruit " fruit ", testInt" testInt
   END FOR
END FUNCTION

This doesn't do what I want, it increments the counter but doesn't skip the rest of the loop cycle, and then the counter is incremented AGAIN at the bottom, so "carrot" never prints out, etc. I'd like to avoid using GOTO if possible. Any ideas?
 
destruk
Posts: 2720
Joined: Sat Dec 18, 2010 4:58 pm

Re: How to skip an iteration in a FOR loop?

Mon Jun 03, 2019 8:26 am

FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR EACH fruit IN testA
      testInt++
      IF TYPE(fruit) = "roString" THEN
           ? fruit
      ELSE
           Next
      END IF
      ? "testNext() did one step, fruit " fruit ", testInt" testInt
   END FOR
END FUNCTION
 
User avatar
speechles
Posts: 169
Joined: Thu Aug 06, 2015 11:15 pm

Re: How to skip an iteration in a FOR loop?

Tue Jun 04, 2019 10:21 am

What exactly are you trying to do? Why are you increment in the for each loop?

FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   for fruit = 0 to testA.count()-1
       if type(testA[fruit]) = "roString" ? testA[fruit]
       ? "testNext(): did one step; fruit="+testA[fruit].toStr()+" index="+fruit.toStr()
   next fruit
END Function

Wouldn't that be easier.. I mean sorta? Are you just trying to build a string of names of fruit from among a non sorted one dimensional array? What exactly are you trying to do sir.. lol

Is shorter better or does adding that extra reference to the array mean it slows down the code and longer is better. You be the judge. you need a huge array to test the millisecond differences. In a list small as this the difference is NIL.

----------------------------------------------------------------
For some reason the Roku docs do not note the special use of "next varname" as an option.

Take this for example:
for fruit = 0 to testA.count()-1
for potion = 0 to testB.count()-1
for skill = 0 to testC.count()-1

Now at any time we can "Next fruit" or "Next potion" or "Next skill" and not involve the other nested for loops incrementing. Using "End for" will interact with the last nested for. Using "next varname" will increment the loop for the associated varname.

Why isn't this in the Roku documentation?

@RokuTannerD This is an oversight and should be corrected. You can use "Next varname" when using "For varname=" in a loop. When doing this it allows incrementing nested for's out of order which the "End for" does not allow. Thanks. ^_~

https://developer.roku.com/docs/references/brightscript/language/program-statements.md

it is that page that is incorrect --^

Also.. why can't we

For each {varname1 varname2 varname3} in var ? Other languages allow this but not brightscript.
 
User avatar
Komag
Topic Author
Posts: 808
Joined: Fri Aug 22, 2014 3:42 am

Re: How to skip an iteration in a FOR loop?

Tue Jun 04, 2019 6:48 pm

destruk, that gives me:

Syntax Error. (compile error &h02) in pkg:/source/mn.brs(1846)

which is the line with Next
 
User avatar
Komag
Topic Author
Posts: 808
Joined: Fri Aug 22, 2014 3:42 am

Re: How to skip an iteration in a FOR loop?

Tue Jun 04, 2019 7:09 pm

speechles, that's very interesting about using NEXT Var in place of END FOR.

(The integer increment was just for information on the printout to help me clarify what was going on.)

Basically I'm trying to process objects in an array, and if the object has a certain property, do all the rest of the processing, otherwise I want to skip to the next object. My current solution is to simply make it a huge IF block, indenting over dozens of lines of code, which aesthetically I'd rather not do but it works just fine. So really this thread is more academic and not really important.
 
destruk
Posts: 2720
Joined: Sat Dec 18, 2010 4:58 pm

Re: How to skip an iteration in a FOR loop?

Wed Jun 05, 2019 8:31 am

Komag wrote:
destruk, that gives me:

Syntax Error. (compile error &h02) in pkg:/source/mn.brs(1846)

which is the line with Next

That is odd.  Perhaps they can not be mixed, but all of my loops I write for my own apps use Next instead of End For.
So I'll need to test and see if replacing End For here with Next resolves that.
Next is a reserved word in brightscript and I was always under the impression they (End For and Next) are interchangeable.

FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR EACH fruit IN testA
      testInt++
      IF TYPE(fruit) = "roString" THEN
           ? fruit
      ELSE
           Next
      END IF
      ? "testNext() did one step, fruit " fruit ", testInt" testInt
   Next
END FUNCTION
 
User avatar
squirreltown
Posts: 870
Joined: Sun Apr 21, 2013 2:20 pm

Re: How to skip an iteration in a FOR loop?

Wed Jun 05, 2019 9:31 am

NEXT does not work for me  inside that if statement. Syntax error.
Kinetics Screensavers
 
destruk
Posts: 2720
Joined: Sat Dec 18, 2010 4:58 pm

Re: How to skip an iteration in a FOR loop?

Thu Jun 06, 2019 9:04 am

squirreltown wrote:
NEXT does not work for me  inside that if statement. Syntax error.

Weird, ok, you are right.  It can't be within the IF statement.
But this works fine if you rewrite the loop slightly.  And if you're wanting the index value of the array for the printed results, you should increment the value after the print statement.
Sub Main()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR EACH fruit IN testA
      IF TYPE(fruit) = "roString" THEN
           ? fruit
      ? "testNext() did one step, fruit " fruit ", testInt" testInt
      END IF
      testInt++
  Next
End Sub
 
destruk
Posts: 2720
Joined: Sat Dec 18, 2010 4:58 pm

Re: How to skip an iteration in a FOR loop?

Thu Jun 06, 2019 9:06 am

Just for kicks I tried, and yes, End For can't be within the If statement either, so it's consistent. Other languages (like PHP) allow this - next will exit any subsequent nested if statements and increment the internal loop counter and re-execute the inner-most loop, just not brightscript.
 
belltown
Posts: 1465
Joined: Thu Dec 09, 2010 1:43 pm
Contact:

Re: How to skip an iteration in a FOR loop?

Thu Jun 06, 2019 10:44 am

Why not just let the loop construct handle the counter:

Sub Main()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   FOR i = 0 TO testA.Count() - 1
      fruit = testA[i]
      IF TYPE(fruit) = "roString" THEN
           ? i; ": "; fruit
      END IF
    END FOR
End Sub


 0: apple
 2: carrot
 3: dapple
 5: fapple
 6: gourd
https://github.com/belltown/
 
User avatar
Komag
Topic Author
Posts: 808
Joined: Fri Aug 22, 2014 3:42 am

Re: How to skip an iteration in a FOR loop?

Fri Jun 07, 2019 8:34 am

My whole point was to NOT process stuff sometimes, so that the counter results would be sequential, such as:
 1: apple
 2: carrot
 3: dapple
 4: fapple
 5: gourd

but apparently that can only be done by working with big IF statements and lots of indenting!
FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR EACH fruit IN testA
      IF TYPE(fruit) = "roString"
         testInt++
         ? "testNext() found a String, fruit " fruit ", testInt" testInt
         ' And do 50 more lines of code,
         ' all indented to be within this huge IF block,
         ' instead of just skipping to next item in list,
         ' too bad
         ' Could maybe use GOTO but that's not something I like to do,
         ' So the IF block with indenting is the lesser of two evils!
      END IF
   END FOR
END FUNCTION
 
User avatar
speechles
Posts: 169
Joined: Thu Aug 06, 2015 11:15 pm

Re: How to skip an iteration in a FOR loop?

Fri Jun 07, 2019 9:28 am

FUNCTION testNext()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   index = 0
   while index < testA.count()
       fruit = testA[index]
       if type(fruit) = "string" then 'do stuff
       index++
   end while 'wend
END Function

The while/endwhile (while/wend) is probably a better choice. You can iterate the array at any moment you like forward _and_ backwards in any increment. For has a limitation of iteration forward only.

So you know apple has a numeric after it to tell the power of the apple when you eat how much it fills you up. Different apples fill up your hunger differently.

If type(fruit) = "string"
   if fruit = "apple"
       fill = testA[index+1]
       m.hunger -= fill ' eat the apple
       ' skip to next entry and skip value assigned to apple
       index +=2
       

Still not sure what you want to do but If I knew I bet I could figure out how to do what you want.. ^_~
Last edited by speechles on Fri Jun 07, 2019 9:42 am, edited 5 times in total.
 
User avatar
squirreltown
Posts: 870
Joined: Sun Apr 21, 2013 2:20 pm

Re: How to skip an iteration in a FOR loop?

Fri Jun 07, 2019 9:35 am

FUNCTION testNext()

   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   testInt = 0
   FOR i = 0 to testA.count()-1
        IF TYPE( testA[i]) = "roString"
         testInt++
         ? "testNext() found a String, fruit " testA[i] ", testInt" testInt
        ELSE
        END IF
   END FOR
END FUNCTION



testNext() found a String, fruit apple, testInt 1
testNext() found a String, fruit carrot, testInt 2
testNext() found a String, fruit dapple, testInt 3
testNext() found a String, fruit fapple, testInt 4
testNext() found a String, fruit gourd, testInt 5
Kinetics Screensavers
 
User avatar
Komag
Topic Author
Posts: 808
Joined: Fri Aug 22, 2014 3:42 am

Re: How to skip an iteration in a FOR loop?

Fri Jun 07, 2019 6:10 pm

speechles wrote:
Still not sure what you want to do but If I knew I bet I could figure out how to do what you want.. ^_~

I literally just wanted to avoid indenting a lot of lines in a big IF block.

If I could just disqualify an Item on the list and say "Next" and have it skip the rest of the FOR loop code for this iteration, then the rest of the FOR loop wouldn't have to be written within an indented IF block, but rather just be lines that are not indented.

Thank you for the WHILE loop example, and I like how it gives more manual control, but the same issue still applies, need to use an indented IF block.
 
belltown
Posts: 1465
Joined: Thu Dec 09, 2010 1:43 pm
Contact:

Re: How to skip an iteration in a FOR loop?

Sat Jun 08, 2019 10:59 am

In general, putting large blocks of code inside nested IF statements (or even using multiple nested IF statements) is considered poor programming practice, so you're on the right track. However, you can easily avoid this by separating out the fruit-processing code into its own function:

Function doFruit(num As Integer, fruit As String)
    ' Do all the fruit processing here ... '
    ? num; ": "; fruit
End Function

Sub Main()
   testA = ["apple", 2, "carrot", "dapple", 5, "fapple", "gourd"]
   num = 0
   For Each fruit In testA
      If Type(fruit) = "roString" Then doFruit(num, fruit) : num++
   End For
End Sub


 0: apple
 1: carrot
 2: dapple
 3: fapple
 4: gourd

EDIT: Put the num++ statement before or after the doFruit() function call depending on whether you want the fruit list to start at 1 or zero.
https://github.com/belltown/

Who is online

Users browsing this forum: No registered users and 5 guests