Programming Forums

Programming Forums (http://www.programmingforums.org/forumindex.php)
-   Python (http://www.programmingforums.org/forum43.html)
-   -   Python brevity (http://www.programmingforums.org/showthread.php?t=9890)

DaWei May 21st, 2006 8:51 AM

Python brevity
 
Obviously, some Python brevity is of the same type as the C/C++ ternary operator, which is to say, not really more efficient, but more efficient to write. How much do you use this in your Python? Here's an example:
:

    for sets in re.finditer (pattern, doc, re.I):
        medList.append ([found for found in sets.group (1, 2, 3) if found != None])
    tagList.append (medList)

The second line is an example, and all three lines could be combined. How much of this do you do? Just curious.

Arevos May 21st, 2006 12:59 PM

I think it depends on how easy it appears to read. As a general rule of thumb, I try to keep list comprehensions under 80 characters long.

hydroxide May 22nd, 2006 2:16 AM

Quote:

Originally Posted by DaWei
Obviously, some Python brevity is of the same type as the C/C++ ternary operator, which is to say, not really more efficient, but more efficient to write. How much do you use this in your Python? Here's an example:
:

    for sets in re.finditer (pattern, doc, re.I):
        medList.append ([found for found in sets.group (1, 2, 3) if found != None])
    tagList.append (medList)

The second line is an example, and all three lines could be combined. How much of this do you do? Just curious.

In general I'd make that five lines (and if the listcomp were complicated I'd use more):
:

    for sets in re.finditer(pattern, doc, re.I):
        matches = [found for found in sets.group (1, 2, 3)
                      if found is not None] # "is not" is safer practice in general
        medList.append (matches)
    tagList.append (medList)

It's rare that a function in Python will go over a page for me. If it does, I try to split things up. For me the extra fraction of a second overhead in the funccall is neither here nor there and readability should trump brevity. The entire structure isn't there, but assuming that you're gathering tags all at the same time, I'd probably use a generator instead:
:

    def gather(pattern, doc):
        yield [[found for found in sets.group (1, 2, 3)
                  if found is not None]
                for sets in re.finditer(pattern, doc, re.I)]

    def run():
        taglist = [gather(pattern, doc)
                      for pattern, doc in fetchlist()]
        use(taglist)

-T. (Gnaaah - code appears as non-monospaced for me - hope it looks ok)

Arevos May 22nd, 2006 3:25 AM

I'd design it with a slightly more general purpose "gather" function, myself:
:

def gather(sets, groups):
    for found in sets.group(*groups):
        if found is not None: yield

found = re.finditer (pattern, doc, re.I)

medList = [x for x in gather(sets, (1, 2, 3)) for sets in found]

Although, on the other hand, if gather will only be used once, it seems a little redundant to wrap it in a separate function.

DaWei May 22nd, 2006 6:09 AM

Please explain to me why "is not" is safer practice....

Arevos May 22nd, 2006 6:16 AM

I think it's just more human-readable than "not (x is y)". I don't believe it has any other significance.

DaWei May 22nd, 2006 6:20 AM

Well, I can easily accept that. I don't know from generators, I'll have to put that in lesson 2.

DaWei May 22nd, 2006 8:40 AM

:

if found is not None
means: if 'found' is not the same object as 'None'
:

if found != None
means: 'found' is not equal to 'None'

I am a total Python noob. That means ignorant, or uninformed; not stupid. Please do not mislead me while I'm trying to learn, whether it's to promote yourself as a guru, or high-priest, or for any other reason. If you care to give a rational dissertation on why one of the above is safer than the other (particularly in this circumstance), please feel free to do so. I'll certainly read it with all my attention.

Arevos May 22nd, 2006 9:55 AM

Quote:

Originally Posted by DaWei
I am a total Python noob. That means ignorant, or uninformed; not stupid. Please do not mislead me while I'm trying to learn, whether it's to promote yourself as a guru, or high-priest, or for any other reason.

Sorry, I merely misunderstood what you were asking.

I thought you were asking why "x is not y" is used instead of "not (x is y)", a question that I've pondered before (because whilst "is not" makes sense in English, it makes less sense from a programming perspective). I didn't realise you were asking the difference between "==" and "is".

As for why "is" should be used instead of "==" for checking None, well, in most cases, it doesn't matter. However, Python objects can overide certain operators (as in C++), thus it's possible that an object will tell you that it is equal to None, without actually being None.

Using "is" ensures that the object really is (or is not) None in all circumstances.

DaWei May 22nd, 2006 10:36 AM

It wasn't directed at you, Arevos, it was directed at the rewriting of my code from
:

medList.append ([found for found in sets.group (1, 2, 3) if found != None])
to
:

if found is not None] # "is not" is safer practice in general
which is an explicit tutorial comment. In fact, the thread HAS been educational. I diverted from my course long enough to go check out generators. I see their utility, but it isn't applicable in this case. The code exists in one place and gets two passes (one for each of two classes of tags). Of particular value to me was discovering the packer/unpacker capability (*group) along the way.


All times are GMT -5. The time now is 4:54 AM.

Powered by vBulletin® Version 3.7.0, Copyright ©2000 - 2008, Jelsoft Enterprises Ltd.
Copyright ©2007 DaniWeb® LLC