用于布尔评估赋值的Python惯用法

时间:2012-09-12 00:58:56

标签: python

我有以下C程序作为我希望在python中能够做的事情的一个例子:

foo@foo:~/$ cat test.c 
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>

bool get_false(){
    return false;
}

bool get_true(){
    return true;
}

void main(int argc, char* argv[]){

    bool x, y;

    if ( x = get_false() ){
        printf("Whiskey. Tango. Foxtrot.\n");
    }   

    if ( y = get_true() ){
        printf("Nothing to see here, keep moving.\n");
    }   
}
foo@foo:~/$ gcc test.c -o test
test.c: In function ‘main’:
test.c:13: warning: return type of ‘main’ is not ‘int’
foo@foo:~/$ ./test 
Nothing to see here, keep moving.
foo@foo:~/$ 

在python中,我知道如何做到这一点的唯一方法是:

foo@foo:~/$ cat test.py
def get_false():
    return False

def get_true():
    return True

if __name__ == '__main__':
    x = get_false()
    if x:
        print "Whiskey. Tango. Foxtrot."

    y = get_true()
    if y:
        print "Nothing to see here, keep moving."

    #if (z = get_false()):
    #    print "Uncommenting this will give me a syntax error."

    #if (a = get_false()) == False:
    #    print "This doesn't work either...also invalid syntax."
foo@foo:~/$ python test.py
Nothing to see here, keep moving.

为什么呢?因为我想能够说:

if not (x=get_false()): x={}

基本上我正在处理一个错误的API,其中返回的类型是数据可用时的dict,或者是False。是的,一个有效的答案是返回一致的类型,并为故障模式指示器使用Exceptions而不是False。我无法更改底层API,并且我在Python之类的环境中使用动态类型(在没有严格键入函数/方法接口的情况下)会遇到这种模式。

有关如何减少if / else开销的任何建议?

3 个答案:

答案 0 :(得分:5)

您可以使用

x = get_false() or {}

如果get_false()返回False值,Python将返回or的第二个操作数。

请参阅Python参考手册的section 5.10。 (自at least Python 2.0以来一直存在。)

答案 1 :(得分:1)

您正在将一个不方便的API与重复的错误补丁代码混合在一起,从而使您想要避免的问题更加复杂。

def wrapper():
    x = get_false()
    if not x:
        x = dict()
    return x

然后,您的代码中不会出现难以阅读的三元(或类似三元)操作,如果您发现更合适,可以更改包装器以引发异常。

你不能做的是在C中作为条件赋值; Python不会这样做。

答案 2 :(得分:0)

您可以使用Python ternary operator

>>> data=False    # could be data=readyourapi()
>>> x=data if data else {}
>>> x
{}