Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.python > #86439 > unrolled thread
| Started by | Mark Lawrence <breamoreboy@yahoo.co.uk> |
|---|---|
| First post | 2015-02-25 20:45 +0000 |
| Last post | 2015-02-27 00:37 +1100 |
| Articles | 8 — 5 participants |
Back to article view | Back to comp.lang.python
Python Worst Practices Mark Lawrence <breamoreboy@yahoo.co.uk> - 2015-02-25 20:45 +0000
Re: Python Worst Practices Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2015-02-26 10:54 +1100
Re: Python Worst Practices Chris Angelico <rosuav@gmail.com> - 2015-02-26 11:26 +1100
Re: Python Worst Practices Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2015-02-26 23:26 +1100
Re: Python Worst Practices Chris Angelico <rosuav@gmail.com> - 2015-02-27 00:12 +1100
Re: Python Worst Practices wxjmfauth@gmail.com - 2015-02-25 22:46 -0800
Re: Python Worst Practices m <mvoicem@gmail.com> - 2015-02-26 14:12 +0100
Re: Python Worst Practices Chris Angelico <rosuav@gmail.com> - 2015-02-27 00:37 +1100
| From | Mark Lawrence <breamoreboy@yahoo.co.uk> |
|---|---|
| Date | 2015-02-25 20:45 +0000 |
| Subject | Python Worst Practices |
| Message-ID | <mailman.19215.1424897186.18130.python-list@python.org> |
http://www.slideshare.net/pydanny/python-worst-practices Any that should be added to this list? Any that be removed as not that bad? -- My fellow Pythonistas, ask not what our language can do for you, ask what you can do for our language. Mark Lawrence
[toc] | [next] | [standalone]
| From | Steven D'Aprano <steve+comp.lang.python@pearwood.info> |
|---|---|
| Date | 2015-02-26 10:54 +1100 |
| Message-ID | <54ee60af$0$13001$c3e8da3$5496439d@news.astraweb.com> |
| In reply to | #86439 |
Mark Lawrence wrote: > http://www.slideshare.net/pydanny/python-worst-practices > > Any that should be added to this list? Any that be removed as not that > bad? I have no idea about Python worst practices, but I think using some sort of Powerpoint slide is surely one of the worst practices in general. In my browser, I see the title "Python Worst Practices". There's a Next Slide button, but clicking it does nothing. Down below, there is what appears to be a transcript, but it is full of extraneous and unnecessary fluff (nearly every line has a leading "Daniel Greenfeld @pydanny") and the formatting is destroyed. Worst practices: - Using assert for error checking, instead of explicit tests. - Overuse of regexes. If the only tool you have is the regex hammer, everything looks like a nail. - Underuse of regexes: failing to use a regex when one is called for is not quite as bad as the regex hammer, but still. - Python is not Java. http://dirtsimple.org/2004/12/python-is-not-java.html http://dirtsimple.org/2004/12/java-is-not-python-either.html Most worst practices are independent of the language. Regardless of whether they are writing Python, C or Ocaml, too many programmers make these deadly programming sins: - Too much coupling. Possibly the Mother Of All Sins, many other sins are variations of this: spaghetti code, ravioli code, global variables, etc. - Premature optimization. Which usually means, optimizing without measurement. If you just *assume* this code is "faster", chances are excellent that it is actually slower. - Overuse of 1-character or excessively generic variable names. - The other extreme: extremely_long_variable_names_for_no_good_reason. - Variable names (including functions and classes!) that aren't self-explanatory. - Misusing Hungarian notation. Or failing to use it when appropriate. http://www.joelonsoftware.com/articles/Wrong.html - Violating the Rule of Demeter: don't talk to the dog's leg, talk to the dog. Or another way to put it: don't let the paper boy reach into your pocket for money. And very possibly the worst practice of all: - Failing to understand when it is, and isn't, appropriate to break the rules and do what would otherwise be a bad practice. -- Steven
[toc] | [prev] | [next] | [standalone]
| From | Chris Angelico <rosuav@gmail.com> |
|---|---|
| Date | 2015-02-26 11:26 +1100 |
| Message-ID | <mailman.19226.1424910410.18130.python-list@python.org> |
| In reply to | #86450 |
On Thu, Feb 26, 2015 at 10:54 AM, Steven D'Aprano
<steve+comp.lang.python@pearwood.info> wrote:
> - Violating the Rule of Demeter: don't talk to the dog's leg, talk to
> the dog. Or another way to put it: don't let the paper boy reach
> into your pocket for money.
I'd call that code smell, rather than an automatic worst practice. Suppose this:
class Shelf:
def __init__(self):
self.items = [] # Empty shelf
bookshelf = Shelf()
bookshelf.items.append(book)
To enforce Demeter, you'd have to add a bunch of methods to the Shelf
whose sole purpose is to pass word along to the items list. Sure, it
makes some design sense to say "Add this book to the shelf" rather
than "Add this book to the items on the shelf", but all those lines of
code are potential bugs, and if you have to reimplement huge slabs of
functionality, that too is code smell. So there are times when it's
correct to reach into another object.
But the times to use two dots are much rarer than the times to use one
dot (the paper boy shouldn't reach into your pocket for money, but
ThinkGeek has your credit card number on file so you can order more
conveniently), and I can't think of any example off-hand where you
would want more than three dots.
ChrisA
[toc] | [prev] | [next] | [standalone]
| From | Steven D'Aprano <steve+comp.lang.python@pearwood.info> |
|---|---|
| Date | 2015-02-26 23:26 +1100 |
| Message-ID | <54ef10e8$0$12984$c3e8da3$5496439d@news.astraweb.com> |
| In reply to | #86454 |
Chris Angelico wrote: > On Thu, Feb 26, 2015 at 10:54 AM, Steven D'Aprano > <steve+comp.lang.python@pearwood.info> wrote: >> - Violating the Rule of Demeter: don't talk to the dog's leg, talk to >> the dog. Or another way to put it: don't let the paper boy reach >> into your pocket for money. > > I'd call that code smell, rather than an automatic worst practice. Well, I did end my post with: And very possibly the worst practice of all: - Failing to understand when it is, and isn't, appropriate to break the rules and do what would otherwise be a bad practice. :-) > Suppose this: > > class Shelf: > def __init__(self): > self.items = [] # Empty shelf > > bookshelf = Shelf() > bookshelf.items.append(book) > > To enforce Demeter, you'd have to add a bunch of methods to the Shelf > whose sole purpose is to pass word along to the items list. Sure, it > makes some design sense to say "Add this book to the shelf" rather > than "Add this book to the items on the shelf", but all those lines of > code are potential bugs, and if you have to reimplement huge slabs of > functionality, that too is code smell. So there are times when it's > correct to reach into another object. Yes, well this comes down to the question of encapsulation and information-hiding. The advantage of exposing the list of items to the public is that anyone can add or remove items, sort them, reverse them, etc. The disadvantage is that you are now committed to keeping that list as part of the public API and you can't easily change the implementation. In this specific example, I'd probably keep the list as part of the Shelf API, although I'd be tempted to make self.items a read-only property. That will allow you to call list mutator methods, but prevent you from doing something silly like: bookshelf.items = 23 > But the times to use two dots are much rarer than the times to use one > dot (the paper boy shouldn't reach into your pocket for money, but > ThinkGeek has your credit card number on file so you can order more > conveniently), and I can't think of any example off-hand where you > would want more than three dots. The Law of Demeter is not really about counting dots. Ruby encourages chaining methods. Python doesn't, since built-ins typically don't return self. But in your own classes, you can have methods return self so you can chain them like this: mylist.append(spam).insert(1, eggs).append(cheese).sort().index(ham) Five dots or not, this is not a violation of Demeter. Likewise for long package names: from mylibrary.audiovisual.image.jpeg import Handler The Law of Demeter is more about information hiding. Clearly you don't hide *public* attributes of your class, otherwise they aren't public, so it's perfectly acceptable to say: myshelf.items.append(spam).insert(1, eggs).append(cheese).sort().index(ham) if items is public. But if the Shelf designer decides that the user shouldn't know anything about how the shelf stores its items, then the *first* dot violates the Law of Demeter. -- Steven
[toc] | [prev] | [next] | [standalone]
| From | Chris Angelico <rosuav@gmail.com> |
|---|---|
| Date | 2015-02-27 00:12 +1100 |
| Message-ID | <mailman.19254.1424956384.18130.python-list@python.org> |
| In reply to | #86494 |
On Thu, Feb 26, 2015 at 11:26 PM, Steven D'Aprano
<steve+comp.lang.python@pearwood.info> wrote:
> Chris Angelico wrote:
>
>> But the times to use two dots are much rarer than the times to use one
>> dot (the paper boy shouldn't reach into your pocket for money, but
>> ThinkGeek has your credit card number on file so you can order more
>> conveniently), and I can't think of any example off-hand where you
>> would want more than three dots.
>
> The Law of Demeter is not really about counting dots. Ruby encourages
> chaining methods. Python doesn't, since built-ins typically don't return
> self. But in your own classes, you can have methods return self so you can
> chain them like this:
>
> mylist.append(spam).insert(1, eggs).append(cheese).sort().index(ham)
>
> Five dots or not, this is not a violation of Demeter. Likewise for long
> package names:
>
> from mylibrary.audiovisual.image.jpeg import Handler
Yes, there are other places where you have lots of dots... I'm talking
about the "rule of thumb" shorthand for describing the Law of Demeter,
which is that you shouldn't have more than one dot before your method
call. The chaining isn't that, because each one is a separate entity;
but if you say "fred.house.bookshelf.items.append(book)", you're
reaching in far too deep - you should be giving Fred the book to place
on his own shelf. That's the only way where "counting dots" is a valid
shorthand. It's mentioned in the Wikipedia article for the law:
https://en.wikipedia.org/wiki/Law_of_Demeter#In_object-oriented_programming
Can you offer a less ambiguous way to describe Demeter violations? By
the "counting dots" style, Demeter demands one, I would be happy with
two, and three or more strongly suggests a flawed API or overly-tight
coupling - with the exception that module references don't get counted
("import os; os.path.append(p)" is one dot, because there's no point
having an "os.add_path()" method). In some languages, those module
references would be notated differently (os::path.append(p)), so
simply counting dots would be closer to accurate. Is there a better
Python description?
ChrisA
[toc] | [prev] | [next] | [standalone]
| From | wxjmfauth@gmail.com |
|---|---|
| Date | 2015-02-25 22:46 -0800 |
| Message-ID | <646615ef-d3cf-427a-94e7-e8b353c9bb53@googlegroups.com> |
| In reply to | #86439 |
Le mercredi 25 février 2015 21:46:42 UTC+1, Mark Lawrence a écrit : > http://www.slideshare.net/pydanny/python-worst-practices > > Any that should be added to this list? Any that be removed as not that bad? > > -- > My fellow Pythonistas, ask not what our language can do for you, ask > what you can do for our language. I searched for a non ascii char. I did not find one [0, 61] slides. jmf
[toc] | [prev] | [next] | [standalone]
| From | m <mvoicem@gmail.com> |
|---|---|
| Date | 2015-02-26 14:12 +0100 |
| Message-ID | <54ef1bb8$0$2175$65785112@news.neostrada.pl> |
| In reply to | #86439 |
W dniu 25.02.2015 21:45, Mark Lawrence pisze: > http://www.slideshare.net/pydanny/python-worst-practices > > Any that should be added to this list? Any that be removed as not that bad? > I disagree with slide 16. If I wanted to use long variable names, I would still code in Java. regards m.
[toc] | [prev] | [next] | [standalone]
| From | Chris Angelico <rosuav@gmail.com> |
|---|---|
| Date | 2015-02-27 00:37 +1100 |
| Message-ID | <mailman.19256.1424957869.18130.python-list@python.org> |
| In reply to | #86496 |
On Fri, Feb 27, 2015 at 12:12 AM, m <mvoicem@gmail.com> wrote:
> W dniu 25.02.2015 21:45, Mark Lawrence pisze:
>>
>> http://www.slideshare.net/pydanny/python-worst-practices
>>
>> Any that should be added to this list? Any that be removed as not that
>> bad?
>>
>
>
> I disagree with slide 16. If I wanted to use long variable names, I would
> still code in Java.
Clearly you aren't bothered by ambiguities, given that your name is
"m". You're lower-case m, and the James Bond character is upper-case
M... yeah, this isn't going to be a problem, with seven billion people
on the planet!
In case it's not obvious from slide 17, the author is advocating
neither the ridiculously short, nor the ridiculously long. This is a
topic that you could go into great detail on, but a general rule of
thumb is that short names go with short-lived variables, and longer
names go with large-scope variables. [1] So your function names
shouldn't be single letters, but your loop counters can and should be
short:
def discard_all_spam():
for msg in self.messages:
if msg.is_spam(): ms.discard()
And of course, the use of "i" as an integer loop index dates back so
far and is so well known that you don't need anything else:
def get_password():
for i in range(4):
if i: print("%d wrong tries...")
s = input("What's the password? ")
if validate_password(s): return s
print("Too many wrong tries, go away.")
This isn't Java coding.
ChrisA
[1] Yes, Python doesn't have variables per se. But how else am I
supposed to differentiate between the name and the concept of a name
binding?
[toc] | [prev] | [standalone]
Back to top | Article view | comp.lang.python
csiph-web