E05 - Mot le plus long⚓︎
Le problème
Proposition 1⚓︎
🐍 Script Python
def mot_le_plus_long(chaine_caractère: str) -> int:
"""Cette fonction prend en paramètre une chaine de caractère et renvoie le nombre de caractère du plus long mot de cette chaine.
>>> 74
ecrivez une fonction qui trouve la longueur du plus long mot dans ce texte
8
"""
chaine_caractère = chaine_caractère.split()
mot = ""
for x in chaine_caractère:
if len(mot) < len(x):
mot = x
return len(mot)
# tests
import doctest
doctest.testmod()
# Entrée
nb_caractère = int(input())
chaine_caractère = input()
# Sortie
print(mot_le_plus_long(chaine_caractère))
- Algorithme bizarre : confusion entre les mots et les lettres.
mot
n'est pas le meilleur choix, c'est la longueur qu'il vaut mieux conserver et mettre à jour.- Revoir le doctest.
- Ne pas faire de ligne de code trop longue. Maximum 80 caractères.
Proposition 2⚓︎
🐍 Script Python
def recherche_mot_long(liste_mots : list) -> int:
""" Renvoie la longueur du mot le plus long de la liste
>>> recherche_mot_long(['bonjour','salutation','coucou'])
10
>>> recherche_mot_long(['ahahah','ok','voiture'])
7
"""
longeur_plus_longue = len(liste_mots[0])
for x in range(1,len(liste_mots)):
if len(liste_mots[x]) > longeur_plus_longue:
longeur_plus_longue = len(liste_mots[x])
return longeur_plus_longue
# tests
import doctest
doctest.testmod()
# Entrée
nb_caractère = int(input())
liste_mots = list(input().split())
# Sortie
print(recherche_mot_long(liste_mots))
split
, c'est tricher ici aussi.- On préfère faire le découpage dans la fonction, pas avant.
Proposition 3⚓︎
🐍 Script Python
nombre_caractères = int(input())
liste_mots = input().split(" ")
# On crée une liste où, à la place d'avoir les mots, on a leur longueur en utilisant `map`
liste_longueur_mots = list(map(len, liste_mots))
# Et on affiche la plus grande longueur de la liste des longueurs de mots
print(max(liste_longueur_mots))
- On attendait une fonction, surtout pour présenter ici un style fonctionnel.
- Quitte à avoir un style fonctionnel, ne pas créer de liste intermédiaire, mais travailler plutôt avec un itérateur.
- Présenter cette variante avec
split
en commentaire après avoir résolu le problème sans.
Proposition 4⚓︎
🐍 Script Python
def mot_le_plus_long(phrase : str) -> int:
"""Renvoie la longueur du plus long mot.
>>> mot_le_plus_long('ecrivez une fonction qui trouve la longueur du plus long mot dans ce texte')
8
"""
liste = phrase.split()
plus_grand_mot = ""
for i in liste:
if (len(plus_grand_mot) < len(i)):
plus_grand_mot = i
print(len(plus_grand_mot))
# Test
import doctest
doctest.testmod()
# Entrées
nb_lettres = int(input())
phrase = input()
if not (0 <= nb_lettres <= 200):
raise ValueError("Trop de lettres")
# Sortie
mot_le_plus_long(phrase)
i
etplus_grand_mot
: mauvais noms.- Le
raise
est inutile ici ; les fichiers d'entrée sont censés être bons.
Proposition 5⚓︎
🐍 Script Python
def cherche_mot_long(nb_caractère: int, phrase):
""" trouve le mot le plus long dans la phrase
et renvoie le nombre du plus grand caractère
>>> cherche_mot_long(74, ['ecrivez', 'une', 'fonction', 'qui', 'trouve', 'la', 'longueur', 'du', 'plus', 'long', 'mot', 'dans', 'ce', 'texte'])
8
"""
if nb_caractère > 200:
raise ValueError("nombre de caractère trop grand")
else:
longeur_mot = len(phrase[0])
for x in phrase:
if len(x) >= longeur_mot:
longeur_mot = len(x)
return longeur_mot
import doctest
doctest.testmod()
nb_caractère = int(input())
phrase = input().split()
print(cherche_mot_long(nb_caractère, phrase))
- Quitte à utiliser un
split
, il vaut mieux le faire dans la fonction. x
: mauvais nom,mot
c'est mieux.raise
inutile.
Proposition 6⚓︎
🐍 Script Python
def mot_le_plus_long(texte):
""" Cette fonction prend en paramètre une chaine de caractères, et elle renvoie le nombre de caractères du plus long mot de cette chaine.
Je n'ai pas activer le test, car celui-ci faisait bugger le programme et je ne sais pas comment le rendre juste.
# >>> mot_le_plus_long(ecrivez une fonction qui trouve la longueur du plus long mot dans ce texte)
8
"""
ans = ""
for lettre in texte:
if len(lettre)>len(ans):
ans = lettre
return ans
# tests
import doctest
doctest.testmod()
# Entrée
nb_caractères = int(input())
texte = input().split()
# Sortie
print(len(mot_le_plus_long(texte)))
- Il manque des guillemets au texte dans le doctest.
- Il faut mettre le
split
(si on l'utilise) dans la fonction. lettre
: mauvais nom d'identifiant.mot
serait mieux.ans
: c'est pas top, c'est une abréviation d'un mot anglais (answer).
Soit on code en anglais, soit en français. Le mélange n'est pas fabuleux...
Proposition 7⚓︎
🐍 Script Python
# 0- Coeur du programme
def mot_le_plus_long(nb_lettres: int, chaine_mots: list) -> int:
""" Renvoie le nombre de caractère du plus long mot de chaine_mots
>>> mot_le_plus_long(11, ["Hello", "World"])
5
>>> mot_le_plus_long(74, ["ecrivez", "une", "fonction", "qui", "trouve", "la", "longueur", "du", "plus", "long", "mot", "dans", "ce", "texte"])
8
"""
plus_long = 0
for mot in chaine_mots:
longueur_mot = len(mot)
if longueur_mot > plus_long:
plus_long = longueur_mot
return plus_long
# 1- Tests
import doctest
doctest.testmod()
# 2- Lecture des entrées
nb_lettres = int(input())
chaine_mots = input().split()
# 3- Appel de la fonction / Sortie
print(mot_le_plus_long(nb_lettres, chaine_mots))
- Il faut mettre le
split
(si on l'utilise) dans la fonction. - Aérer le doctest.
- Au lieu de passer une liste en paramètre, il vaut mieux la chaine.
- C'est plus cohérent avec la longueur donnée aussi en paramètre.
plus_long
: on peut faire mieux avecplus_grande_longueur
.
Proposition 8⚓︎
🐍 Script Python
def longueur_max_mot(texte : str) -> int :
""" Renvoie l'entier correspondant à la longueur du plus long mot
de la chaine de caractère 'texte'.
>>> texte = 'ecrivez une fonction qui trouve la longueur du plus long mot dans ce texte'
>>> longueur_max_mot(texte)
8
"""
max = 0
for mot in texte :
if len(mot) > max :
max = len(mot)
return max
# tests
import doctest
doctest.testmod()
# Entrée
nb_caractères = int(input())
assert 1 <= nb_caractères <= 200
texte = input().split()
# Sortie
print(longueur_max_mot(texte))
- Bon doctest, mais il échoue, en cause : le
split
placé avant l'appel à la fonction. assert
inutile.- L'annotation de type est fausse ; pour le corriger, il faut placer le
split
dans la fonction... max
ettexte
ne sont pas des noms idéaux.
Corrigé du professeur⚓︎
🐍 Script Python
"""
author: Franck CHAMBON
problem: https://prologin.org/train/2003/semifinal/mot_le_plus_long
"""
def longueur_plus_long_mot(chaine: str) -> int:
"""Renvoie la longueur du mot le plus long.
>>> longueur_plus_long_mot("ecrivez une fonction qui trouve\
la longueur du plus long mot dans ce texte")
8
>>> longueur_plus_long_mot("aaa b")
3
>>> longueur_plus_long_mot("a bbb")
3
>>> longueur_plus_long_mot("cc")
2
"""
taille = len(chaine)
longueur_max = 0
longueur = 0
for i in range(taille):
if chaine[i] == ' ':
if longueur_max < longueur:
longueur_max = longueur
longueur = 0
else:
longueur += 1
# test du dernier mot
if longueur_max < longueur:
longueur_max = longueur
return longueur_max
import doctest
doctest.testmod()
taille = int(input())
chaine = input()
print(longueur_plus_long_mot(chaine))
- On conseille d'ajouter des tests utiles simples en plus de ceux proposés par le problème. Des cas délicats (corner cases en anglais).
- On peut proposer en bonus une version fonctionnelle courte :
🐍 Script Python
def longueur_plus_long_mot(chaine: str) -> int:
return max(map(len, chaine.split()))
map
renvoie un itérateur et aucune liste intermédiaire n'est créée.