Live data from Hacker News

Anti-Patterns in Python Programming

lignos.org

171–180 of 242 posts

Re: Anti-Patterns in Python Programming

#171
post #168

Earlier quoted context omitted.

I'll tell you what I tell my team: it's barely more verbose, and the readability is up for extremely serious debate (I mean, everyone understands nested for loops, but the nested list comprehension thing is wierd... why is something that appears way way before the innermost "for" the same as something in that for loop's declaration?) It may also be less efficient. When I'm shown numbers that the difference between th…

When I see a list comprehension I can see with a single glance what it's doing. Not so with the 4 line for loop. Comprehensions aren't a strange language feature in Python either...it's one of the central features of Python. Don't use something until it's proven to yield a great benefit is a very conservative approach. That may be appropriate in some cases, but I'm very glad that I am not in such a team since that wo…

I'm talking strictly about multi "for" comprehensions. They just are too confusing to me and most of the people I've worked with ever. But we also use lots (most) python features fully, just that one has been the source of dozens of bugs in this one codebase, not to mention others I've worked on with other people. It is a shitty non-intuitive syntax.

Nested for loops, flatten(), various itertools functions and chained generator expressions all suffice, and I have yet to see them provide measurable slowdown to actual code compared to good algorithms and decent factoring. Like I said, I'll even use multi-for comprehensions if there is a measurable difference over nested for-loops.

Also, I think you are intentionally misrepresenting what I said - when I said don't use "weird stuff" I explicitly excluded idiomatic language things. That includes (for python) single for comprehensions. The multi-for comprehension is something I rarely come across in the wild despite it's long time existence in python - it's a weird one.

Re: Anti-Patterns in Python Programming

#172

Earlier quoted context omitted.

Yes that is correct. The default value gets created when the function is interpreted ("compiled").

> The default value gets created when the function is interpreted ("compiled"). No. The default value gets "created" (the expression is evaluated and stored) when the def statement is executed. Take the following example: In [1]: def foo(): ...: def append_five(l=[]): ...: l.append(5) ...: return l ...: return append_five ...: In [2]: a = foo() In [3]: b = foo() In [4]: a() Out[4]: [5] In [5]: b() Out[5]: [5] In [6]:…

I thought that was what he meant. Is there any sharp distinction between "interpreting" and "evaluating" in python that I am unaware of? I've always used the words more or less interchangeably. But now that I think about it that might be a little naive since I have no idea how it works under the hood

Re: Anti-Patterns in Python Programming

#173

Failing to use join is a big one. I have seen countless instances of people writing the logic to output commas in between items (like for CSV export) that they want to concatenate into a string. header_line = ','.join( header for header in headers ) csv_line = ','.join( str(dataset[key]) for key in dataset.keys() ) Example for a case of a dictionary mapping a string to a bunch of numbers.

Any reason not to do the first one more compactly?

     ','.join(headers)

Re: Anti-Patterns in Python Programming

#174

Earlier quoted context omitted.

If it's so subtle, does it matter? This sounds like you just have a problem with the word "tuple" applied to an object that behaves differently from tuples in a statically-typed language. Would you feel better if they named it "ImmutableList" instead?

Can't speak for GP, but I would [feel better with that name]. (Although I agree with you that statically-typed-language-tuples don't seem to make sense in Python.) But hey... Python's weird choice of how to name the ImmutableList could be worse, right? For example, someone could be malicious enough to call their general-purpose associative array a "hash", just because a hashmap (note: not a hash) is a good implementa…

Not really that important, but I think map is a better name than associative array.

Re: Anti-Patterns in Python Programming

#175

Failing to use join is a big one. I have seen countless instances of people writing the logic to output commas in between items (like for CSV export) that they want to concatenate into a string. header_line = ','.join( header for header in headers ) csv_line = ','.join( str(dataset[key]) for key in dataset.keys() ) Example for a case of a dictionary mapping a string to a bunch of numbers.

Proper Python would use the csv module for this operation, as your CSV export would break if `header` or `dataset[key]` contains a comma.

Re: Anti-Patterns in Python Programming

#176

Failing to use join is a big one. I have seen countless instances of people writing the logic to output commas in between items (like for CSV export) that they want to concatenate into a string. header_line = ','.join( header for header in headers ) csv_line = ','.join( str(dataset[key]) for key in dataset.keys() ) Example for a case of a dictionary mapping a string to a bunch of numbers.

[deleted]

Re: Anti-Patterns in Python Programming

#177
post #54

Earlier quoted context omitted.

Don't know if this is why , but the list comprehension takes an expression at the "foo(word)" location, and is therefore more general than map, which requires a function. The comprehension in that case is simpler. words = ['w1', 'w2', 'w3'] [word[1] for word in words] ['1', '2', '3'] map(lambda x: x[1], words) ['1', '2', '3'] I like looking at the list comprehension better. The use of lambda looks forced in this case…

In that case I'd use map(itemgetter(1), words)

Instead of my map example, or instead of a list comprehension in general?

Re: Anti-Patterns in Python Programming

#178
post #160

Earlier quoted context omitted.

> if an object is immutable, the behavior of Python matches what the naive developer expects If the object was immutable then append wouldn't work. That's hardly matching expectations.

Read my post that has the "correct answers" which show you how to do it. The key is setting the default to None and then doing something like: if val is None: val = [] or the more idiomatic python way: val = val or []

I'm well aware of that way to do it, but it doesn't excuse a different way being unintuitive.

Re: Anti-Patterns in Python Programming

#179
post #148

Question, how do you over multiple long lists (in python 2) especially if zip itself takes a long time to zip them, for example.

You use Python 3. J/K, while this is technically a limitation of Python 2, there actually is izip in itertools package which is a generator and works in similar way to zip in python 3.

Awesome! I knew there was some lazy zip-ish thing for python 2. I personally hate using range(len(foo)) as anyone else.

Re: Anti-Patterns in Python Programming

#180
post #6

Earlier quoted context omitted.

Possibly the most interesting anti-pattern I saw was: a_list_of_words = "my list of words".split(" ") I never enquired why, since there were bigger issues in the code e.g. "unit testing" by running the code, taking the result and putting it as the check value. By running repr(value), copying out the string then comparing self.assertEqual(repr(value), '[ , ...]')

perhaps that line was written by someone used to Perl, where they would have had @a_list_of_words = qw/my list of words/; there

You'd be sure if they wrote:

    >>> qw = str.split
    >>> qw('my list of words')
    ['my', 'list', 'of', 'words']
Post reply on HN