[Python-ideas] breaking out of module execution

Steven D'Aprano steve at pearwood.info
Wed Apr 25 18:54:58 CEST 2012

Mark Shannon wrote:
> I would have taken these to be the disadvantages, rather costs.
> By costs, I assumed you meant implementation effort or runtime overhead.

No, costs as in "costs versus benefits".

> Also, I don't see the difference between a return in a module, and a 
> return in a function. Both terminate execution and return to the caller. 
> Why do these four points apply to module-level returns any more than 
> function-level returns?

A very good point. There is a school of thought that functions should always 
have a single entry (the top of the function) and a single exit (the bottom). 
If I recall correctly, Pascal is like that: there's no way to return early 
from a function in Pascal.

However, code inside a function normally performs a calculation and returns a 
value, so once that value is calculated there's no point hanging around. The 
benefit of early return in functions outweighs the cost. It is my argument 
that this is not the case for top level module code.

Some differences between return in a function and return in a module:

1) Modules don't have a caller as such, so it isn't clear what you are 
returning too. (If the module is being imported, I suppose you could call the 
importing module the caller; but when the module is being run instead, there 
is no importing module.) So a top level return is more like an exit than a 
return, except it doesn't actually exit the Python interpreter.

2) When functions unexpectedly return early, you can sometimes get a clue why 
by inspecting the return value. Modules don't have a return value.

3) Functions tend to be relatively small (or at least, they should be 
relatively small), so while an early return in the middle of a function can be 
surprising, the cost of discovering that is not very high. In contrast, 
modules tend to be relatively large, hundreds or even thousands of lines. An 
early return could be anywhere.

4) Code at the top level of modules is usually transparent: the details of 
what gets done are important. People will want to know which functions, 
classes and global variables are actually created, and which are skipped due 
to an early return. In contrast, functions are usually treated as opaque 
blackboxes: people usually care about the interface, not the implementation. 
So typically they don't care whether the function returns out early or not.

There may be other differences.

>> Today, if you successfully import a module, you know that all the 
>> top-level code in that module was executed. If this feature is added, 
>> you cannot be sure what top-level code was reached unless you scan 
>> through all the code above it.
>> [end quote]
> I don't know if this is a good idea or not, but the fact that to it can
> be implemented by removing a single restriction in the compiler suggests
> it might have some merit.

Do you really mean to say that *because* something is easy, it therefore might 
be a good idea?

rm -rf /

Easy, and therefore a good idea, yes? *wink*


More information about the Python-ideas mailing list