Linux Bash Continue in for Loop

Commands affecting loop behavior

break, continue

The break and continue loop control commands [1] correspond exactly to their counterparts in other programming languages. The break command terminates the loop (breaks out of it), while continue causes a jump to the next iteration of the loop, skipping all the remaining commands in that particular loop cycle.

Example 11-21. Effects of break and continue in a loop

#!/bin/bash  LIMIT=19  # Upper limit  echo echo "Printing Numbers 1 through 20 (but not 3 and 11)."  a=0  while [ $a -le "$LIMIT" ] do  a=$(($a+1))   if [ "$a" -eq 3 ] || [ "$a" -eq 11 ]  # Excludes 3 and 11.  then    continue      # Skip rest of this particular loop iteration.  fi   echo -n "$a "   # This will not execute for 3 and 11. done   # Exercise: # Why does the loop print up to 20?  echo; echo  echo Printing Numbers 1 through 20, but something happens after 2.  ##################################################################  # Same loop, but substituting 'break' for 'continue'.  a=0  while [ "$a" -le "$LIMIT" ] do  a=$(($a+1))   if [ "$a" -gt 2 ]  then    break  # Skip entire rest of loop.  fi   echo -n "$a " done  echo; echo; echo  exit 0

The break command may optionally take a parameter. A plain break terminates only the innermost loop in which it is embedded, but a break N breaks out of N levels of loop.

Example 11-22. Breaking out of multiple loop levels

#!/bin/bash # break-levels.sh: Breaking out of loops.  # "break N" breaks out of N level loops.  for outerloop in 1 2 3 4 5 do   echo -n "Group $outerloop:   "    # --------------------------------------------------------   for innerloop in 1 2 3 4 5   do     echo -n "$innerloop "      if [ "$innerloop" -eq 3 ]     then       break  # Try   break 2   to see what happens.              # ("Breaks" out of both inner and outer loops.)     fi   done   # --------------------------------------------------------    echo done    echo  exit 0

The continue command, similar to break, optionally takes a parameter. A plain continue cuts short the current iteration within its loop and begins the next. A continue N terminates all remaining iterations at its loop level and continues with the next iteration at the loop, N levels above.

Example 11-23. Continuing at a higher loop level

#!/bin/bash # The "continue N" command, continuing at the Nth level loop.  for outer in I II III IV V           # outer loop do   echo; echo -n "Group $outer: "    # --------------------------------------------------------------------   for inner in 1 2 3 4 5 6 7 8 9 10  # inner loop   do      if [[ "$inner" -eq 7 && "$outer" = "III" ]]     then       continue 2  # Continue at loop on 2nd level, that is "outer loop".                   # Replace above line with a simple "continue"                   # to see normal loop behavior.     fi        echo -n "$inner "  # 7 8 9 10 will not echo on "Group III."   done     # --------------------------------------------------------------------  done  echo; echo  # Exercise: # Come up with a meaningful use for "continue N" in a script.  exit 0

Example 11-24. Using continue N in an actual task

# Albert Reiner gives an example of how to use "continue N": # ---------------------------------------------------------  #  Suppose I have a large number of jobs that need to be run, with #+ any data that is to be treated in files of a given name pattern #+ in a directory. There are several machines that access #+ this directory, and I want to distribute the work over these #+ different boxen. #  Then I usually nohup something like the following on every box:  while true do   for n in .iso.*   do     [ "$n" = ".iso.opts" ] && continue     beta=${n#.iso.}     [ -r .Iso.$beta ] && continue     [ -r .lock.$beta ] && sleep 10 && continue     lockfile -r0 .lock.$beta || continue     echo -n "$beta: " `date`     run-isotherm $beta     date     ls -alF .Iso.$beta     [ -r .Iso.$beta ] && rm -f .lock.$beta     continue 2   done   break done  exit 0  #  The details, in particular the sleep N, are particular to my #+ application, but the general pattern is:  while true do   for job in {pattern}   do     {job already done or running} && continue     {mark job as running, do job, mark job as done}     continue 2   done   break        # Or something like `sleep 600' to avoid termination. done  #  This way the script will stop only when there are no more jobs to do #+ (including jobs that were added during runtime). Through the use #+ of appropriate lockfiles it can be run on several machines #+ concurrently without duplication of calculations [which run a couple #+ of hours in my case, so I really want to avoid this]. Also, as search #+ always starts again from the beginning, one can encode priorities in #+ the file names. Of course, one could also do this without `continue 2', #+ but then one would have to actually check whether or not some job #+ was done (so that we should immediately look for the next job) or not #+ (in which case we terminate or sleep for a long time before checking #+ for a new job).

Caution

The continue N construct is difficult to understand and tricky to use in any meaningful context. It is probably best avoided.

negretemovendays.blogspot.com

Source: https://tldp.org/LDP/abs/html/loopcontrol.html

0 Response to "Linux Bash Continue in for Loop"

Post a Comment

Iklan Atas Artikel

Iklan Tengah Artikel 1

Iklan Tengah Artikel 2

Iklan Bawah Artikel