如何优化我的if else循环python?

时间:2014-03-07 09:28:48

标签: python

有没有办法在python中优化我的if else条件?

if not is_text or not is_archive or not is_hidden or \
      not is_system_file or not is_xhtml or not is_audio or not is_video: 
                is_unrecognised = True
else: 
      #get the value which is True out of 
      #is_text,  is_archive,  is_hidden, is_system_file,
      #is_xhtml, is_audio, is_video

我觉得以这种方式编写if条件可能是个坏主意。所以我把它们分成了函数并编写了代码。但是我们可以优化我的代码以使其感觉可读且高效吗?

8 个答案:

答案 0 :(得分:4)

  1. 阅读De Morgan's laws

    “不(A和B)”与“(不是A)或(不是B)”

  2. 相同
  3. all(iterable):如果iterable的所有元素都为true(或者iterable为空),则返回True。 any(iterable):如果iterable的任何元素为true,则返回True。如果iterable为空,则返回False

    conditions = (  # make a tuple: an iterable
       is_text, 
       is_archive, 
       is_hidden, 
       is_system_file, 
       is_xhtml, 
       is_audio, 
       is_video
     )
    
     if not all(conditions): # apply De Morgans
         is_unrecognised = True
     else:
        # other code
    

  4. 顺便说一句,如果符合您的要求,可以进一步简化,而不是

    is_unrecognised = not all(conditions)
    # may be you can write
    # if not is_unrecognised:
    #    you code in else 
    

答案 1 :(得分:3)

布尔代数满足De Morgan定律,

(De Morgan 1) (¬x)∧(¬y) = ¬(x∨y)
(De Morgan 2) (¬x)∨(¬y) = ¬(x∧y).

因此您可以将其更改为

if not ( is_text and is_archive and is_hidden and is_system_file and is_xhtml and is_audio and is_video):
    is_unrecognised = True
else: 
    #get the value which is True out of 
    #is_text,  is_archive,  is_hidden, is_system_file,
    #is_xhtml, is_audio, is_video

答案 2 :(得分:3)

首先,我会尝试使用try: except:而不是if: else:。它更快,因为我不完全理解。唯一的问题是你的陈述必须提高异常。

另一种方法是这样做:

if False in [is_text, is_archive, is_hidden, is_system_file, is_xhtml, is_audio, is_video]:

答案 3 :(得分:3)

看起来你必须确切地知道哪些条件是真的。在这种情况下,我建议像这样写:

if is_text: # do something elif is_archive: ... elif is_video: # do something else: is_unrecognised = True

此结构类似于其他语言中的switchcase语句。

修改:是的,正如评论中所建议的那样,您的原始代码可能包含and而不是or。所以它就像:如果它是(1)不是文字(2)不是视频(...)不是所有其他可识别的东西,那么它未被承认。

答案 4 :(得分:1)

我认为最简单和Pythonic的做法是对@Grijesh的回答进行一些修改。即,

conditions = (
    is_text, 
    is_archive, 
    is_hidden, 
    is_system_file, 
    is_xhtml, 
    is_audio, 
    is_video
)

is_unrecognised = True if not any(conditions) else False

答案 5 :(得分:1)

到目前为止,其他人说的是正确的,您可以使用De Morgan's laws并重写if测试。

但是,据我所知,目前最大的问题是,如果我正确理解你的代码,它就不会按照你的想法做到。

你真正想要的似乎是

if not (is_text or is_archive or is_hidden or \
  is_system_file or is_xhtml or is_audio or is_video): 
            is_unrecognised = True

if not any(is_text, is_archive, is_hidden, is_system_file, is_xhtml, is_audio, is_video): 
            is_unrecognised = True

编辑:或者Gassa的解决方案似乎更符合您实际尝试的目标。

答案 6 :(得分:1)

您的数据表示可能会让您误入歧途。如果相反你做了像

这样的事情
tests = dict()
testkeys = ['text', 'archive', 'hidden', 'system', 'xhtml', 'audio', 'video']
[tests[i] = False for i in testkeys]

# whatever code you have now to set is_text should now instead set tests['text'], etc

if not True in tests.values():
    is_unrecognized = True
else:
    recognized = [k for k in tests if tests[k] is True]  # f'rinstance

(我确信有更多惯用的方法可以做到这一点。只是建议一种不同的思维模式,真的。)

答案 7 :(得分:1)

即使这个问题已经得到解答。我提出了一个替代方案,其中包含问题代码中的注释。

正如@tripleee所指出的,代码注释中提出的原始问题是获取值为True的变量。

@ tripleee的答案假设用变量名创建一个字典。

另一种方法是从locals获取名称。以下代码

is_text = False
is_archive = True
is_hidden = False
is_system_file = False
is_xhtml = False
is_audio = True
is_video = False
the_size = 34 # <- note also this
conditions = (
               is_text,
               is_archive,
               is_hidden,
               is_system_file,
               is_xhtml,
               is_audio,
               is_video,
               the_size,
               )

result = [(k, v) for k, v in list(locals().iteritems()) \
          if id(v) in [id(condition) for condition in conditions] and v]

if len(result) == 0:
    is_unrecognized = True
else:
    # do what you want with your variables which have value True
    # as example print the variable names and values
    for k, v in result:
        print 'variable "%s" is %s' % (k, v)