Perl and Python

gnat on 2003-09-03T16:21:18

So Rael (my virtual cubemate) has been experimenting with Python and was raving about its readability. I downloaded his flav2theme doodad and had a crack at porting it to Perl. It didn't take long, but I had to ask him wtf some things did first (e.g., hash.get() and os.path.splitext).

What didn't bother me about Perl: dollar signs and curly braces. In fact, I found it harder to figure out the Python code structure because of the indents-with-no-curlies and the weird "if I am main" stuff at the top.

What did bother me about Perl: having to say or die, and I suffered at the hands of Perl's clumsy filename parsing libraries. How many times should one write open without or die? Not many. Then again, I don't want hash lookups to throw an exception when the element doesn't exist, so DWIMmery means inconsistency.

Clumsy filename parsing libraries? Yes. The os.path library seems so much more aimed at what people actually want to do than the fugly File::Spec and File::Basename. In particular, the acts of removing directories and extensions are easy in Python and hard in Perl. Perl makes you use a regular expression to describe suffixes. Oy.

Python turned out to have its own weird idioms. You can treat a string like an array, subscripting into it. I initially wrote my code to have an array of lines, thinking this must be how the file was read. Nope. And because accessing an nonexistent element of a hash throws an exception, Rael used an idiom where you catch that exception to deal with the case where the element doesn't exist. I prefer Perl's more direct if (exists ...) { ... } else { ... } to that.

Of course, Rael may well be writing illiterate chicken-scratching Python (I could believe it, having seen his Perl and PHP :-) but I think in this case that the equivalent Perl was, where the standard libraries didn't break down, easier to understand than the original Python.

Next on the Fair and Balanced(tm) Flame News Channel, I try vi and find it lacking! We retort, you deride!

--Nat


splitext is cleaner?

da on 2003-09-03T17:22:45

From the python docs, it appears that os.path.splitext will always assume the extension contains at most one period, which according to p. 328 of Perl Cookbook (1st ed. :-) is just why File::Basename requires a regular expression: Consider ".tar.gz"- is the extension ".tar", ".gz.", or ".tar.gz"? By specifying the pattern, you control which of these you get.

So yes, the default for python looks cleaner; but it's less flexible. In the best of all worlds: perhaps File::Basename::fileparse should default to the pattern "\..*" to be more DWIMy.

Come to think of it, is File::Basename that fugly as-is? Wouldn't something like:

($junk, $component, $flavour) = fileparse($file, "\..*"); look clearer than:

($component, $flavour) = $file =~ m{^.*/(.*)(\..*)$}; # extract suffix

(speaking as somebody who knows no python; and hasn't used fileparse much. Maybe you had a reason to avoid fileparse I didn't see!)

uhmmm...

LTjake on 2003-09-03T17:33:48

Was that script supposed to work? It chokes hard on a perl -c. Mostly from not declaring variables. It also has a syntax error on this line

$page = sprintf("\n";

(missing left bracket)

And interesting look at perl and python none the less.

Yay Python

Dom2 on 2003-09-03T19:27:29

Well, I found it easier to read. :-)

My complaint about the python code is that __main__ stuff. It's just not needed at all in that script. It's only needed in the case you have a module and you want it to do something if it's executed as well.

But then again, I love the idea of the language actually forcing you to be consistent with yourself when you're indenting. Most of the complaints I see about python state that it forces you to indent according to a certain set of rules. This is crap. All you have to do is be consistent in your own rules. Obviously most people find this too hard...

Ah, enough flamebait!

-Dom

-Dom

Perl v. Python

ziggy on 2003-09-03T20:35:43

I took a brief gander at the Perl and Python versions in that order.

My first impression, after reading each in the browser for about a second each:

  • The Perl version starts with a nice long comment that describes WTF this script does.
  • The Python version starts out with gobs of plaintext
  • Oh, wait, it's not python code
  • Oh, wait, it starts out with """
  • Oh, wait, that's a triple-quoted strong. Where does it end?
  • Oh, wait, the python program starts out with pretty much the same commentary as the Perl program.
  • Oh, wait, the commentary is much the same, but it takes more effort to figure out where the comment is here...[*]
Now we see why C programmers highlight multiline comments with asterisks on every line, and why C++ introduced the // comment marker.

Embedding plaintext comments with a pair of multiline comment markers is a baaad idea. It forces too many neurons to fire when you don't have the benefit of syntax coloring...

 

*: Yes, you could make the same accusations about embedding Pod in a Perl program. But we have different social conventions on when to use pod and when to use comments. And a lot of Pod is found at the end of the file, where there is no overhead to figure out where the program is in a morass of multiline comments...

Re:Perl v. Python

dws on 2003-09-03T22:37:46

I found the Python """ idiom to be no harder to get used to than HEREDOCs.

Re:Perl v. Python

ziggy on 2003-09-03T22:41:07

...but we don't use HEREDOCs for block comments.

Re:Perl v. Python

dws on 2003-09-03T23:25:54

You've never seen anyone use a HEREDOC for a block comment? You've lived a sheltered life.

That particular block comment is special. Python associates it with the class object as a special documentation string (__doc__, iirc).

Re:Perl v. Python

Dom2 on 2003-09-04T07:14:51

The beauty of the triple quoted string is that the documentation is then part of the code. It's available as __doc__ and available to be referenced from your code. Now you can do nice things with it like provide online help automatically from classes / methods.

-Dom

Re:Perl v. Python

babbage on 2003-09-04T22:30:57

  • The Perl version starts with a nice long comment that describes WTF this script does.
  • The Python version starts out with gobs of plaintext.

Then the files aren't really equivalent. Python's """ foo """ multiline comment construct is more equivalent to Perl's POD, not to heredocs.

Now if you want to complain about the readability of POD, that's one thing, but it's not fair to criticise the Python script for using the language's documentation mechanism when the equivalent comment in the Perl script would have been using POD to accomblish the same thing.

Otherwise, the Python could have been written as normal pound-sign delimted single-line comments, at which point the two versions are both semantically and syntactically equivalent and your objectsions dissolve in a puff of smoke... :-)

Re:Perl v. Python

ziggy on 2003-09-04T22:58:51

it's not fair to criticise the Python script for using the language's documentation mechanism when the equivalent comment in the Perl script would have been using POD to accomblish the same thing.
I'm not criticizing the script, I'm criticizing the language.

This isn't about docstrings vs. comments, or Pod vs. triple-quoted strings. It's about making different things look different. The combination of triple-quoted strings and their use as docstrings hurts readability because you have to parse them to see where the doc/comment ends and where the code begins. #-style and //-style comments don't have that issue.

You can sling similar arrows at Pod, but there are ways to structure programs so that Pod and code are separate. Docstrings, however, force these docs to be smushed in front of code (something remarkably similar visual structure).

And while this Python program could start with #-comments, there's a big pressure to make this a docstring.

Fatal

koschei on 2003-09-03T23:38:56

use Fatal qw( open close );