开发者

Python: avoiding if condition?

开发者 https://www.devze.com 2022-12-23 01:23 出处:网络
Which is be开发者_Python百科tter? if not var: var = get_var() (or) var = var or get_var() Also, How do I know the better of the two?

Which is be开发者_Python百科tter?

if not var:
    var = get_var()
(or)

var = var or get_var()

Also, How do I know the better of the two?

edit:

One more option from steve,

var = var if var else get_var()


The better is the one you like better. I would use first version with if but this is very personal.


When two style variations are so close stylistically, I use timeit as the tie-breaker: faster must mean closer to Python's mainstream, i.e., better. Hey, it's better than endless debate, y?-) So:

$ python -mtimeit -s'var=0; getvar=lambda:0' 'var = var or getvar()'
1000000 loops, best of 3: 0.359 usec per loop
$ python -mtimeit -s'var=0; getvar=lambda:0' 'if not var: var = getvar()'
1000000 loops, best of 3: 0.361 usec per loop
$ python -mtimeit -s'var=1; getvar=lambda:1' 'var = var or getvar()'
10000000 loops, best of 3: 0.123 usec per loop
$ python -mtimeit -s'var=1; getvar=lambda:1' 'if not var: var = getvar()'
10000000 loops, best of 3: 0.0899 usec per loop

the if has it -- equivalent when var is false, faster when it's true.


Actually, if you are trying to determine if var has been previously set using a call to get_var, then I would contend that both forms are wrong. Python treats a number of perfectly ordinary values as evaluating to a boolean 'false': 0, None, [], (,), set(), and {}. So let's say var is going to be an integer, and get_var() happens to return 0. Now, regardless of which form you use, get_var() will get called again and again, even though we already know that var is 0!

There are several methods for detecting whether a variable has been defined or not:

  • look in the dict returned by globals() or locals()

  • wrap the statement var = var in a try/except block, trapping on NameError

  • use a sentinel value like None, and initialize var to this value; then you can test for if var is None: var = get_var() (using 'is', not '=='). If you are unlucky, and None is a potential value to be returned from get_var(), then you'll need to define your own special not-yet-defined value, using something like NOT_DEFINED = object(), initialize var with it, and then you can test for if var is NOT_DEFINED.


To me, the first idiom, the one using the explicit if, is preferable because more explicit.

However I've seen the or construct being referenced as the preferred / more pythonic one.

So, on the one hand, Explicit is better than implicit (Zen citation), on the other hand, the short expression can be viewed as pythonic (although shorter isn't equivalent to pythonic in all cases!)

A closely related SO question is most idiomatic way to convert None to empty string, and both the if and the or idioms were listed there.


the first version is more intuitive to me. But then again, its all about your own taste.


Second one is more pythonic, and I normally use that.


Neither is wrong.

The former is clearer to understand for someone reading the code.

Ask yourself if, when you are thinking about the problem you are trying to solve, the concepts that come to mind are closer to "if this, then that" or "a logical OR of two almost, but not quite, Boolean variables."


Both will eventually compile to the same code, given that or is a short-circuit operator (it doesn't evaluate the right hand argument if left hand is true).

I'd prefer the first one as it expresses your intent more clearly. The second one is probably more compact.


The interpreter will likely execute them both the way. There are tradeoffs regarding code readability. Which statement is easier to recognize what it does? Certainly, the first is much clearer. For me, reading this post, I had to think more about the second one. I would use the first due to increased readability, even if the second statement is slightly 'sexier'.

Hope this helps.
-tjw

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号