【问题标题】:nested for and if inside a list comprehension嵌套 for 和 if 在列表推导中
【发布时间】:2021-04-25 23:32:53
【问题描述】:

我有以下代码,其中有 for 和 if 可选。

lines = ['apple berry Citrus ', 34, 4.46, 'Audi Apple ']

corpus = [ ]

for line in lines:

    # Check if the element is string and proceed
    if isinstance(line, str):

        # Split the element and check if first character is upper case
        for word in line.split():
            if word[0].isupper():
                
                # Append the word to corpus result
                corpus.append(word)
print(corpus)
# Output : ['Citrus', 'Audi', 'Apple']

我正在尝试在列表理解中执行此操作,但失败了。我已经尝试如下。

# corpus = [  word if word[0].isupper() for word in line.split()  for line in lines if isinstance(line, str)]

如何在列表理解中实现这一点?

【问题讨论】:

    标签: python python-3.x list python-2.7 list-comprehension


    【解决方案1】:

    以下将起作用:

    corpus = [
        word for line in lines if isinstance(line, str) 
             for word in line.split() if word[0].isupper()
    ]
    

    嵌套推导中的范围起初可能会令人困惑,但您会注意到 forif 的顺序与嵌套循环中的顺序相同。

    【讨论】:

      【解决方案2】:

      你可以这样做:

      [word for line in lines if isinstance(line, str) 
           for word in line.split() if word[0].isupper()]
      

      另一种方法是使用filter 预过滤列表lines

      [word for line in filter(lambda e: isinstance(e, str), lines) 
            for word in line.split() if word[0].isupper()]
      

      或者,正如 cmets 中所指出的,您可以使用以下命令消除 lambda

      [word for line in filter(str.__instancecheck__, lines) 
            for word in line.split() if word[0].isupper()]
      

      甚至两个过滤器:

      [word for line in filter(str.__instancecheck__, lines)
            for word in filter(lambda w: w[0].isupper(), line.split())]
      

      【讨论】:

      • 对我来说,第一个过滤器的可读性更多,因为它准确地说明了意图。
      【解决方案3】:

      作为一般规则,您可以将执行 corpus.append(xxxx) 的嵌套循环的内部部分放在列表解析的开头(xxx)。然后添加嵌套的 for 循环和不带 ':' 的条件。

      corpus = [ word                          # from corpus.append(word)
                 for line in lines             # ':' removed ... 
                     if isinstance(line,str) 
                         for word in line.split() 
                             if word[0].isupper() ]
      
      # on a single line:
      corpus = [ word for line in lines if isinstance(line,str) for word in line.split() if word[0].isupper() ]
      
      print(corpus) # ['Citrus', 'Audi', 'Apple']
      

      【讨论】:

        猜你喜欢
        • 2016-11-10
        • 2019-03-03
        • 2021-02-20
        • 2012-08-09
        • 1970-01-01
        • 1970-01-01
        • 2023-03-06
        • 2021-06-04
        • 1970-01-01
        相关资源
        最近更新 更多