"def" vs "sub" (was RE: More random python observations from a perl programmer)

Tim Peters tim_one at email.msn.com
Fri Aug 20 02:47:23 EDT 1999


[posted & mailed]

[tchrist]
> ...
> Python deems def an executable statement.  Perl doesn't.  Therefore,
> it's a gotcha for a Perl programmer, who doesn't understand why the
> silly compiler did that.

That cuts both ways, of course, as does any difference.  That is, I once got
miffed at Perl because my named, nested functions weren't working.  "man
pages" or not <wink>, it wasn't until I studied the source that I figured
out Perl effectively moves all named functions to the top level, and if you
have two nested functions in a package that happen to have the same name,
the first gets tossed into the bit bucket:

$x = 5;

sub outer1 {
    my $x = 50;
    sub inner {
        print "in the first inner, and here's x: $x\n";
    }
    &inner();
}

sub outer2 {
    my $x = 500;
    sub inner {
        print "in the second inner, and here's x: $x\n";
    }
    &inner();
}

&outer1();

Which prints:

    in the second inner, and here's x:

(the first inner vanished, and $x in the second inner is undefined).

It's curious that Python & Perl both *allow* lexical nesting of named
functions, and both do wildly-- yet different! --unexpected things with
them.  Python may not have lexical closures in Perl's sense, but Perl
doesn't have nesting in Python's sense <wink>.

> Apparently, it's just at run-time interring a function that was
> compiled at compile-time in the current symbol table.

Yes, "def" acts exactly like an assignment statement, binding the function
name to the code object in the current local namespace (which happens to be
the module namespace if the function is at top-level, the current function's
local namespace if the "def" is contained in a function, or the class's
namespace if the function is contained in a class).

One cute consequence is stuff like:

if __debug__:
    def f():
        # slow but careful implementation
else:
    def f():
        # fast but caressless implementation

more-powerful-than-a-speeding-#ifdef-ly y'rs  - tim






More information about the Python-list mailing list