[Tutor] Which is better Practice and why

Oscar Benjamin oscar.j.benjamin at gmail.com
Tue Oct 23 14:22:27 CEST 2012


On 23 October 2012 02:17, Devin Jeanpierre <jeanpierreda at gmail.com> wrote:
> On Mon, Oct 22, 2012 at 8:42 PM, Steven D'Aprano <steve at pearwood.info> wrote:
>> If you do that, and the module directly or indirectly imports itself
>> while it is running as a script, you may run into trouble. But writing
>> a dual-purpose module that is usable as an importable module or as a
>> stand-alone script is not problematic in itself.
>
> Yes. However, it is somewhat hard to guarantee that a module won't
> indirectly import itself for a large codebase. It certainly sometimes
> happens by accident.

I guess this is the crux of the issue. If your script is part of and
depends on a large codebase then you may as well place all of its code
elsewhere in the codebase. The script then serves simply as an entry
point and its presence in the project won't hinder your ability to
move all the code it uses around to suit its relationship to the rest
of the codebase.

Importable scripts are useful when you have a codebase that is
smaller. In particular if your codebase is one single script (a common
case) then you should always use if __name__ == "__main__" unless the
script is trivial and/or, as Steven says, you're feeling lazy. Doing
this means that you can test your script and its functions by
importing the script in the interactive interpreter and that you can
reuse the script as a module in some other project

If your codebase is a single module rather than a script, giving it an
if __name__ == "__main__" block allows someone to perform a common
task with the module (or perhaps run its tests) using the -m
interpreter option without needing to turn a single file project into
a double file project:

    $ python -m mymodule arg1 arg2

This is often better than creating a separate script to serve as a
redundant entry point (redundant since the module can already serve as
its own entry point).

Once you have one importable script A.py you can then place another
script B.py in the same folder have B import and use some of A's code.
As Eryksun has said making this work both ways (having B also import
from A) can lead to problems. If you find yourself wanting to do that
then you have probably organised your code badly. As a solution
consider moving all of the common code into one of A or B or into a
new module/script C.

Another factor not mentioned yet is that the use of if __name__ ==
"__main__" is so ubiquitous that using it in your own script
communicates something to most people who read it (including
yourself). If I know that X.py is intended to be used as a script and
I want to read it to find out how it works, one of the first things I
would do is search for that line. My natural assumption is that no
non-trivial execution occurs outside of that if-block (this is almost
always true if I wrote the script and it is longer than about 10
lines).


Oscar


More information about the Tutor mailing list