问题的提出
你参加了一个面试,面试官打算测试你写简明的单行解决方案的技能。因此,他决定给你展示一段长而复杂的代码,看起来很吓人,并要求你为给定的代码想出单行解决方案。
给定
# data
n = 5
# Multi-line Code
for i in range(1, n+1):
print(i, end=" ")
if i == n:
print()
for i in range(1, n):
print(i, end=" ")
if i == n-1:
print()
for i in range(1, n-1):
print(i, end=" ")
if i == n-2:
print()
for i in range(1, n-2):
print(i, end=" ")
if i == n-3:
print()
for i in range(1, n-3):
print(i, end=" ")
挑战
- 猜测上述代码所产生的输出。
- 为给定的多行代码制定一个单行解决方案。
那么,你能接受这个挑战吗?我们强烈建议你在深入研究这里给出的解决方案之前,先试着想出你的解决方案。现在,不要再拖延了,让我们深入研究给定挑战的解决方案。
输出
虽然代码看起来令人生畏,但它只是一个生成特定模式的编码片段,也就是输出。因此,输出看起来像这样。
1 2 3 4 5
1 2 3 4
1 2 3
1 2
1
一旦你掌握了一般的模式,就不会那么困惑了。for 循环被故意序列化,使每个循环负责打印一行数字来混淆你。没有理由像这样嵌套它们。
好了!现在我们有了输出。现在我们有了输出,让我们来制定这个看起来很丑的多行代码的单行解决方案。
方法1:单行For Loop
对于给定的问题,一个直接而简明的单行解决方案是使用一个简单的for循环,然后在print语句中借助range函数生成输出。所有这些都可以在一行代码中完成。
代码
# data
n = 5
# one-liner
for i in range(n, 0, -1): print(*range(1, i + 1))
- 我们的想法是使用for循环在0到n的范围内迭代,步长为1。这样可以确保计数器变量从n开始,即本例中的5,然后向后迭代直到1。负的步长处理了向后迭代的问题。
- 然后,我们在同一行内的循环体中移动,并开始使用
*与range()函数打印模式。该*****允许你 "解包"一个可迭代的对象,这样每个元素都作为一个单独的参数传递,而不是函数作为一个参数接收整个可迭代对象。让我们通过一个例子来直观地了解range()和*range()之间的区别。
>>> print(range(1, 5))
range(1, 5)
>>> print(*range(1, 5))
1 2 3 4 5
# This is the same as printing:
>>> print(1, 2, 3, 4, 5)
1 2 3 4 5
- 你必须打印位于->
(1, i+1)范围内的值,其中i是用于for循环的计数器变量。这实质上意味着你要打印从1开始到i结束的一定范围内的数值。 - 由于外循环从5开始,一直到1。在每个迭代中打印的值如下所示。
- 迭代1:i = 5,打印的值(从1到i)= 1 2 3 4 5
- 迭代1:i = 4,打印的值(从1到i)= 1 2 3 4
- 迭代1:i = 3,打印的值(从1到i)= 1 2 3
- 迭代1:i = 2,打印的值(从1到i)= 1 2
- 迭代1:i = 1,打印的值(从1到i)= 1
方法2:单行嵌套For循环
另一种解决编码难题的方法是在一行代码中使用join() 函数和一个嵌套for循环,如下图所示。
# one-liner
print("\n".join(" ".join(str(j + 1) for j in range(5 - i)) for i in range(5)))
上述单行代码是解决以下多行解决方案的简明单行方式,它产生的输出与给定问题中的输出相同。
for i in range(5):
for j in range(5-i):
print(str(j+1), end=" ")
print()
方法3:使用列表理解和嵌套For循环的单行代码
还有一种方法是在嵌套for循环的帮助下用单行解决这个问题。在这种情况下,我们将从一个由另一个for循环支持的list comprehension中解压输出。列表编译器负责处理每一行产生的输出,而另一个for循环通过迭代range(6,1,-1) 来处理外循环。
代码
# data
n = 5
# one-liner
[print(*[j for j in range(1, i)]) for i in range(6, 1, -1)]
方法4:使用内置函数的单线程
如果你对Python的[内置函数]非常熟悉,那么这个解决方案可能会引起你的注意。
# data
n = 5
# one-liner
print('\n'.join(' '.join(map(str, range(1, i))) for i in range(n + 1, 1, -1)))
# or you can also use the following solution-
for i in range(n+1, 1, -1): print(' '.join(map(str, range(1, i))))
- 上面的单行解决方案再次使用for循环和
map、join函数。for循环允许你在 ->**(n + 1, 1, -1)**范围内向后迭代,其中 -1 表示步长,允许你向后迭代。 - 在每次迭代中,我们使用
map方法将一个从1开始到i-1结束的数值范围转换为一个字符串。这里,i是for循环在每次迭代中返回的值。join方法允许你在每个字符串值之间输入一个空格。
总结
我们已经成功地解决了给定的编程挑战,并制定了多达四个单行的解决方案。我希望这个教程对你有所帮助。