Simple is better than complex

par Vincent Poulailleau - 3 minutes de lecture - 509 mots

Introduction

Je vois passer un post sur LinkedIn qui dit : faites le code le plus simple pour afficher :

*
**
***
****
*****
****
***
**
*

Spoiler : ma solution est à la fin et aussi en image.

Parmi les réponses que les lecteurs ont fournies (oui, elles ont réellement été proposées), en voici quelques-unes.

Solution intuitive pour les débutants

1
2
3
4
for i in range(6):
    print('*' * i)
for i in range(4, 0, -1):
    print('*' * i)

Autre solution moins intuitive, mais compréhensible par les débutants

1
2
3
4
5
for i in range(10):
    if i <= 5:
        print('*' * i)
    else:
        print('*' * (10 - i))

Solution de la personne payée au nombre de caractères

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
def print_row(n):
    print("* " * n)


def print_top_half(n):
    for row in range(1, n + 1):
        print_row(row)


def print_bottom_half(n):
    for row in range(n - 1, 0, -1):
        print_row(row)


def print_triangle(n):
    print_top_half(n)
    print_bottom_half(n)


triangle_height = 5
print_triangle(triangle_height)

Solution sans if

1
2
3
4
5
6
def pyramid(height):
    for num in range(1, 2 * height + 1):
        print('*' * min(num, 2 * height - num))


pyramid(5)

Solution logique, mais difficile à lire au premier coup d’œil

1
print(*(("* " * x) for x in range(1, 5)), *(("* " * x) for x in range(5, 0, -1)), sep='\n')

Solution rusée, mais difficile à lire au premier coup d’œil

1
2
3
from itertools import chain

print(*(("* " * x) for x in chain(range(1, 5), range(5, 0, -1))), sep='\n')

Un peu dans la même idée

1
2
3
4
5
6
7
8
def print_pattern():
    counts = list(range(1,6)) # [1, 2, 3, 4, 5]
    counts += list(range(4,0,-1)) # [1, 2, 3, 4, 5] + [4, 3, 2, 1]
    strs = list(map(lambda c: print("*" * c), counts))
    print("\n".join(strs))


print_pattern()

Un ami de la récursivité

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
def draw_figure(number, constant):
    if number == 0:
        return

    print("*" * (constant - number))
    draw_figure(number - 1, constant)
    print("*" * (constant - 1 - number))


draw_figure(5, 5)

Solution simple, mais difficile à lire au premier coup d’œil

1
print("* \n* *\n* * *\n* * * *\n* * * * *\n* * * *\n* * *\n* *\n*\n")

Ma solution

J’apprécie l’imagination des solutions proposées, certaines ne me seraient jamais passées par l’esprit !

La PEP 20 (https://peps.python.org/pep-0020/) nous dit : « Simple is better than complex ». Nous devons donc, dans la philosophie de Python toujours aller au plus simple. Elle nous dit aussi : « Readability counts », nous devons aller au code le plus lisible.

Mon code sera le suivant :

  • pas de if
  • pas de for
  • juste un print
  • la lisibilité au premier coup d’œil
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
# PEP 20:
# - Simple is better than complex.
# - Readability counts.

print("""\
*
**
***
****
*****
****
***
**
*
""")