循环和列表推导式——Python 5/7

for 和 while循环,和一个被广泛喜爱的Python特质:列表推导式

循环

  • 循环是一种反复执行代码的方式:
planets = ['Mercury', 'Venus', 'Earth', 'Mars', 'Jupiter', 'Saturn', 'Uranus', 'Neptune']
for planet in planets:
    print(planet, end=' ') # print all on same line
Mercury Venus Earth Mars Jupiter Saturn Uranus Neptune
  • for循环要求:
  • 要使用的变量名(这里的planet
  • 要循环遍历的集合(这里的planet
  • 要使用单词in将他们连在一起;
  • in右侧的变量可以是任何能够迭代的对象。一般如果它们可以被看作是一堆事物,那么你基本上就可以循环遍历他们。除了列表,元组中的元素也可以迭代遍历。
multiplicands = (2, 2, 2, 3, 3, 5)
product = 1
for mult in multiplicands:
    product = product * mult
product
360
  • 你甚至可以遍历一个字符串中的各个字符。
s = 'steganograpHy is the practicE of conceaLing a file, message, image, or video within another fiLe, message, image, Or video.'
msg = ''
# print all the uppercase letters in s, one at a time
for char in s:
    if char.isupper():
        print(char, end='')
HELLO

range()函数

  • range()是一个返回一系列数字的函数。他在写循环时非常有用。
  • 比如,如果我们想反复做一个动作5次:
for i in range(5):
    print("Doing important work. i =", i)
Doing important work. i = 0
Doing important work. i = 1
Doing important work. i = 2
Doing important work. i = 3
Doing important work. i = 4

while 循环

  • 另一种循环叫while循环,这个循环会在达到某个条件前一直做同样的操作。
i = 0
while i < 10:
    print(i, end=' ')
    i += 1 # increase the value of i by 1
0 1 2 3 4 5 6 7 8 9
  • while循环的参数是一个计算出的布尔值,并且循环将一直执行,指导条件值为False

列表推导式

  • 列表推导式是Python最独特也是最受欢迎的特质。最简单的理解方法莫过于看几个例子:
squares = [n**2 for n in range(10)]
squares
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
  • 下面是我们不用列表推导式达到同样的目的:
squares = []
for n in range(10):
    squares.append(n**2)
squares
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
  • 我们也可以在其中加if条件:
short_planets = [planet for planet in planets if len(planet) < 6]
short_planets
['Venus', 'Earth', 'Mars']

如果你熟悉SQL语句,你可以把它理解成“where”条件句

  • 这里是一个带if判断并且对循环变量有变形的例子:
# str.upper() returns an all-caps version of a string
loud_short_planets = [planet.upper() + '!' for planet in planets if len(planet) < 6]
loud_short_planets
['VENUS!', 'EARTH!', 'MARS!']
  • 人们通常习惯写在一行,但是你会发现分开三行以上的结构更清晰:
[
    planet.upper() + '!' 
    for planet in planets 
    if len(planet) < 6
]
['VENUS!', 'EARTH!', 'MARS!']

继续和SQL语句比较的话,比可以把这几行认为是SELECT、FROM、和WHERE

  • 左边的表达式技术上不需要循环变量(这样做很不寻常)。
[32 for planet in planets]
[32, 32, 32, 32, 32, 32, 32, 32]
  • 列表推导式与如min max sum的函数结合可以得到一个很棒的一行的解决方案,这种解决方案一般通常需要很多行代码来实现。
  • 例如,比较下面两个代码块,他们实现的是相同的功能:
def count_negatives(nums):
    """Return the number of negative numbers in the given list.
    
    >>> count_negatives([5, -1, -2, 0, 3])
    2
    """
    n_negative = 0
    for num in nums:
        if num < 0:
            n_negative = n_negative + 1
    return n_negative
def count_negatives(nums):
    return len([num for num in nums if num < 0])
  • 好极了,不是吗?
  • 如果我们只是追求精简的代码的话,那么下面的解决方案就更好:
def count_negatives(nums):
    # Reminder: in the "booleans and conditionals" exercises, we learned about a quirk of 
    # Python where it calculates something like True + True + False + True to be equal to 3.
    return sum([num < 0 for num in nums])
  • 那种解决方案是“最好的”完全是一个主观判断。用更少的代码解决问题固然很好,但是遵循下面的Python之禅是十分必要的:
  • 可读性要高
  • 清楚的代码要比含糊的代码要好
  • 所以,使用这些技巧使得代码更紧凑是可以的,但是当你要选择一种使用方法时,最好是大家能看懂的方法。