Anonymous user
Flow-control structures: Difference between revisions
m
Fixed lang tags.
(→CATCH-THROW: Better sentence) |
m (Fixed lang tags.) |
||
Line 6:
===goto===
<lang ada>
===exit===
Exit is used to break out of loops. Exit can be used with a label to break out of an inner loop to an outer loop and its enclosing outer loop
<lang ada>
===asynchronous transfer of control===
A sequence of operation can be aborted with an asynchronous transfer of control to an alternative:
<lang ada>select
delay 10.0;
Put_Line ("Cannot finish this in 10s");
Line 29 ⟶ 28:
-- do some lengthy calculation
...
end select;</lang>
The alternative can be a delay statement or else an entry point call followed by a sequence of operations. The statement blocks at the delay or entry call and executes the sequence of the operation introduced by '''then abort'''. If blocking is lifted before completion of the sequence, the sequence is aborted and the control is transferred there.
Line 41 ⟶ 39:
See also [[Exceptions#ALGOL_68|Exceptions]] to see how '''ALGOL 68''' handles ''transput'' events.
===One common use of a label in '''ALGOL 68''' is to break out of nested loops.===
<lang
FOR j TO 1000 DO
FOR i TO j-1 DO
Line 54 ⟶ 52:
);</lang>
===Multi way jump using labels and '''EXIT''' to return result ===
<lang
[]PROC VOID award = (gold,silver,bronze);
Line 67 ⟶ 65:
print(("Medal awarded: ",medal, new line));</lang>
===Another use is to implement finite state machines ===
<lang
INT condition;
PROC do something = VOID: condition := 1 + ENTIER (3 * random);
Line 89 ⟶ 87:
print(("Final state: ",final state, new line));</lang>
===ALGOL 68G implements a Refinement Preprocessor to aid with top down code development ===
<lang
determine first generation;
WHILE can represent next generation
Line 150 ⟶ 148:
===goto===
One common use of goto in C is to break out of nested loops.
<lang c>
=={{header|C++}}==
=== goto ===
{{works with|GCC|3.3.4}}
<lang cpp>
Note that "goto" may also be used in conjunction with other forms of branching.
Line 182 ⟶ 180:
Exceptions are a way to give control back to a direct or indirect caller in case of an error. Note that throwing exceptions is usually very expensive, therefore they generally should only be used for exceptional situations.
<lang cpp>
=={{header|D}}==
=== goto ===
<lang d>label1:
writeln ("i'm in your infinite loop");
goto label1;</lang>
=== Exceptions ===
D supports standard try/catch/finally mechanisms:
<lang d>void main (char[][] args)
{
try
Line 289 ⟶ 284:
writeln ("finished (exception or none)");
}
}</lang>
=== Scope guards ===
Line 298 ⟶ 292:
For instance:
<lang d>void main (char[][] args)
{
scope (exit) writeln ("gone");
if (args[1] == "throw") throw new Exception ("message");
scope (exit) writeln ("gone, but we passed the first chance to throw an exception");
}</lang>
If the exception is thrown, then the only text that is written to the screen is "gone". If no exception is thrown, both calls to writeln occur.
Line 317 ⟶ 309:
The basic syntax is
}</lang>
Within ''body'' variable ''ej'' then contains a one-argument function (an ejector) which, if called, immediately returns the provided value from the escape block.
Line 350 ⟶ 342:
===goto===
<lang
(This is almost never used)
Line 358 ⟶ 350:
===on_error===
<lang
(This resumes at the label <tt>test</tt> if an error is encountered)
Line 364 ⟶ 356:
===on_ioerror===
<lang
(Same as <tt>on_error</tt>, but for EOFs and read-errors and such)
Line 370 ⟶ 362:
===break===
immediately terminates the innermost current loop (or <tt>if</tt> or <tt>case</tt> etc)
Line 376 ⟶ 368:
===continue===
immediately starts the next iteration of the current innermost loop
Line 399 ⟶ 391:
Goto is typically looked down upon by most Perl programmers
<lang perl>
=={{header|Pop11}}==
Line 408 ⟶ 400:
quitloop with argument exits from nested loops:
<lang pop11>while condition1 do
while condition2 do
if condition3 then
Line 415 ⟶ 406:
endif;
endwhile;
endwhile;</lang>
above quitloop(2) exits from both loops.
Line 425 ⟶ 415:
nested loops:
<lang pop11>while condition1 do
while condition2 do
if condition3 then
Line 433 ⟶ 422:
endwhile;
endwhile;
l:;</lang>
Another use is to implement finite state machines:
<lang pop11>state1:
DO_SOMETHING();
if condition1 then
Line 454 ⟶ 441:
...
stateN:
....</lang>
Pop11 goto is a nonlocal one, so "jump out" from a chain of procedure calls:
<lang pop11>define outer();
define inner(n);
if n = 0 then
Line 469 ⟶ 454:
inner(5);
final:;
enddefine;</lang>
This is useful to exit early from successful recursive search, and for exception handling.
Line 478 ⟶ 462:
go_on is a multiway jump
<lang pop11>go_on expression to lab1, lab2, ..., labN else elselab ;</lang>
If expression has value K the above will jump to label labK, if expression is not an integer, or if it outside range from 1 to N, then control passes to label elselab. The else part may be omitted (then out of range values of expression cause an exception).
Line 499 ⟶ 481:
it is just:
<lang pop11>return;</lang>
but it is also possible to specify one or more return values:
<lang pop11>return(val1, val2, val3);</lang>
===chain===
Line 513 ⟶ 491:
chain has effect of "tail call" but is not necessarily in tail position. More precisely inside proc1.
<lang pop11>chain proc2(x1, x2, x3);</lang>
finishes execution of proc1 and transfers control to the proc2 passing it x1, x2, and x3 as arguments. On return from proc2 control passes to caller of proc1.
Line 524 ⟶ 500:
===Loops===
Python supports ''break'' and ''continue'' to exit from a loop early or short circuit the rest of a loop's body and "continue" on to the next loop iteration.
<lang python># Search for an odd factor of a using brute force:
for i in range(n):
if (n%2) == 0:
Line 534 ⟶ 509:
else:
result = None
print "No odd factors found"</lang>
In addition, as shown in the foregoing example, Python loops support an ''else:'' suite which can be used to handle cases when the loop was intended to search for something, where the code would break out of the loop upon finding its target. In that situation the ''else:'' suite can be used to handle the failure. (In most other languages one is forced to use a "sentinel value" or a special flag variable ... typically set to "False" before the loop and conditionally set to "True" within the loop to handle situations for which the Python ''else:'' on loops is intended).
Line 548 ⟶ 522:
A custom Exception class is normally declared with the ''pass'' statement as no methods of the parent class are over-ridden, no additional functionality is defined and no attributes need be set. Example:
<lang python>class MyException(Exception): pass</lang>
One normally would choose the most similar existing class. For example if MyException was going to be raised for some situation involving an invalid value it might be better to make it a subclass of ValueError; if it was somehow related to issues with inappropriate objects being passed around then one might make it a subclass of TypeError.
Line 558 ⟶ 530:
To create a "virtual base class" (one which is not intended to be directly instantiated, but exists solely to provide an inheritance to it's derived classes) one normally defines the requisite methods to raise "NotImplementedError" like so:
<lang python>class MyVirtual(object):
def __init__(self):
raise NotImplementedError</lang>
It then becomes necessary for any descendants of this class to over-ride the ''__init__()'' method. Any attempt to instantiate a "MyVirtual" object directly will raise an exception.
====Case 1 - Try, Except====
<lang python>try:
# 'except' catches any errors that may have been raised between the code of 'try' and 'except'
except: # Note: catch all handler ... NOT RECOMMENDED
print "An error occurred."
# Output
====Case 2 - Try, Except====
<lang python>try:
# here, 'except' catches a specific type of error raised within the try block.
except ZeroDivisionError:
print "You've divided by zero!"
# Output
====Case 3 - Try, Except, Finally====
<lang python>try:
except:
print "An error occurred."
# here, 'finally' executes when the try - except block ends, regardless of whether an error was raised or not
# useful in areas
finally:
print "End of 'try' block..."
# Output :
# An error occurred
# End of 'try' block...</lang>
Note: Prior to version 2.5 a ''try:'' statement could contain either series of ''except:'' clauses '''or''' a ''finally:'' clause but '''not both.''' It was thus necessary to nest the exception handling in an enclosing ''try:''...''finally:'' loop like so:
<lang python>try:
try:
except (MyException1, MyOtherException):
pass
except SomeOtherException:
finally:
do_some_cleanup() # run in any case, whether any exceptions were thrown or not</lang>
====Case 4 - Try, Except, Else====
<lang python>try:
temp = 1/1 # not a division by zero error
except ZeroDivisionError: # so... it is not caught
print "You've divided by zero."
# here, 'else' executes when no exceptions are caught...
else:
print "No apparent error occurred."
# Output :
# No apparent error occurred.</lang>
====Case 5 - Try, Except, break, continue====
<lang python>i = 0
while 1: # infinite loop
try:
temp = math.sqrt(i)
print "
break # 'break' out of while loop
except ZeroDivisionError:
print "You've divided by zero. Decrementing i and continuing..."
i-=1 # we decrement i.
# we 'continue', everything within the try - except block will be executed again,
# this time however, ZeroDivisionError would not be raised again.
continue # Note that removing it, replacing it with 'pass' would perform the equivalent
# see below for a better example
# Output :
# You've divided by zero. Decrementing i and continuing...
# Imaginary Number! Breaking out of loop</lang>
====Case 6 - Creating your own custom exceptions, raise====
<lang python># Let's call our custom error "StupidError"; it inherits from the Exception class
class StupidError(Exception): pass
# Try it out.
try:
raise StupidError("Segfault") # here, we manually 'raise' the error within the try block
except StupidError, details: # 'details' is
# Output :
# Something stupid occurred: Segfault</lang>
===Case 7 - continue, else in "for" loop===
<lang python> i = 101
for i in range(4): # loop 4 times
print "I will always be seen."
Line 684 ⟶ 639:
if(__name__ == "__main__"):
main()</lang>
===The "with" statement===
Line 691 ⟶ 645:
See [[http://www.python.org/peps/pep-0343.html PEP 0343, The "with" statement]]
<lang python>class Quitting(Exception): pass
max = 10
with open("some_file") as myfile:
exit_counter = 0
for line in
print
The ''with'' statement allows classes to encapsulate "final" (clean-up) code which will automatically be executed regardless of exceptions that occur when working "with" these objects. Thus, for the foregoing example, the file will be closed regardless of whether it's more than 10 lines long. Many built-in and standard library classes have "context managers" which facilitate their use in ''with:'' code. In addition it's possible to define special __enter__() and __exit__() methods in one's own classes which will be implicitly called by the interpreter when an object is used within a ''with:'' statement.
Line 835 ⟶ 787:
This skips the line that changes the value of x to 5.
<lang
=== On Error Goto ===
Line 847 ⟶ 799:
This brances in the event of an error. Usually there is an Exit (Sub|Function) to seperate the normal code from the error handling code
<lang
''This style of code is rarely used.''
Line 861 ⟶ 813:
This performs a sequence of actions. If any action fails, the exception is discarded and next operation is performed.
<lang
''This style of code is rarely used.''
Line 875 ⟶ 827:
This shows the classical and modern syntax for exiting a sub routine early.
<lang
=== Return value / Exit Function ===
Line 889 ⟶ 841:
This shows the classical and modern syntax for exiting a function early. There is an implied variable with the same name as the function. This variable is write-only.
<lang
|