- Fonctions Anonymes (Lambda) en Python
Les fonctions anonymes, également appelées fonctions lambda, sont des fonctions de petite taille qui n'ont pas de nom. En Python, elles sont définies à l'aide du mot-clé lambda. Elles sont limitées à une seule expression.
Syntaxe
lambda arguments: expression
L'expression est évaluée et le résultat est renvoyé. Les fonctions lambda sont souvent utilisées pour des opérations simples où la création d'une fonction nommée complète serait excessive.
# Exemple de fonction lambda simple
resultat_puissance = (lambda base, exposant: base ** exposant)(3, 4)
print(resultat_puissance) # Affiche 81
Les fonctions lambda sont particulièrement utiles en combinaison avec des fonctions d'ordre supérieur comme max(), sorted(), map(), et filter().
Utilisation avec max()
La fonction max() peut prendre un argument key qui est une fonction (souvent une lambda) utilisée pour déterminer la valeur sur laquelle baser la comparaison.
salaires_employes = {
'Alice': 3000,
'Bob': 100000,
'Charlie': 5000,
'David': 2000
}
# Trouver l'employé avec le salaire maximum en utilisant une fonction nommée
def obtenir_salaire(nom_employe):
return salaires_employes[nom_employe]
employe_max_salaire_nomme = max(salaires_employes, key=obtenir_salaire)
print(f"L'employé avec le salaire le plus élevé (fonction nommée) est : {employe_max_salaire_nomme}")
# Trouver l'employé avec le salaire maximum en utilisant une lambda
employe_max_salaire_lambda = max(salaires_employes, key=lambda nom: salaires_employes[nom])
print(f"L'employé avec le salaire le plus élevé (lambda) est : {employe_max_salaire_lambda}")
Utilisation avec sorted()
La fonction sorted() peut trier n'importe quel itérable et peut également utiliser un argument key pour personnaliser l'ordre de tri.
liste_nombres = [1, 5, 6, 3, 99, 3955, 55, 3, 4, 7, 661]
print(f"Liste triée par défaut : {sorted(liste_nombres)}")
# Trier les employés par salaire croissant
noms_tries_par_salaire = sorted(salaires_employes, key=lambda nom: salaires_employes[nom])
print(f"Employés triés par salaire : {noms_tries_par_salaire}")
# Trier les employés par salaire décroissant
noms_tries_par_salaire_inverse = sorted(salaires_employes, key=lambda nom: salaires_employes[nom], reverse=True)
print(f"Employés triés par salaire (décroissant) : {noms_tries_par_salaire_inverse}")
Utilisatino avec map()
La fonction map() applique une fonction donnée à chaque élément d'un itérable et renvoie un itérateur de résultats.
employes_noms = list(salaires_employes.keys())
# Ajouter un suffixe à chaque nom d'employé
noms_transformes = list(map(lambda nom: f'{nom}_DEV', employes_noms))
print(f"Noms transformés : {noms_transformes}")
Utilisation avec filter()
La fonction filter() construit un itérateur à partir des éléments d'un itérable pour lesquels une fonction renvoie True.
liste_chaines = ['pomme', 'banane', 'ananas', 'orange', 'pamplemousse']
# Filtrer les chaînes se terminant par 'ananas' ou 'orange'
chaines_filtrees = list(filter(lambda s: s.endswith('ananas') or s.endswith('orange'), liste_chaines))
print(f"Chaînes filtrées : {chaines_filtrees}")
- Fonctions Intégrées Utiles en Python
Conversion en Octets (bytes())
La fonction bytes() permet de créer des objets bytes (séquences immuables d'octets), souvent en encodant une chaîne de caractères.
message_str = "Bonjour le monde !"
message_bytes_utf8 = message_str.encode('utf-8')
print(f"Chaîne encodée (méthode str) : {message_bytes_utf8}")
message_bytes_func = bytes(message_str, 'utf-8')
print(f"Chaîne encodée (fonction bytes) : {message_bytes_func}")
Conversion ASCII (chr() et ord())
ord(caractère) renvoie la valeur entière ASCII/Unicode d'un caractère. chr(nombre) renvoie le caractère correspondant à une valeur entière.
print(f"Valeur ASCII de 'a' : {ord('a')}")
print(f"Valeur ASCII de 'Z' : {ord('Z')}")
print(f"Caractère pour 97 : {chr(97)}")
print(f"Caractère pour 90 : {chr(90)}")
Division et Reste (divmod())
divmod(x, y) renvoie un tuple contenant le quotient entier et le reste de la division de x par y, équivalent à (x // y, x % y).
print(f"Divmod(10, 3) : {divmod(10, 3)}") # (3, 1)
print(f"Divmod(17, 5) : {divmod(17, 5)}") # (3, 2)
Itération avec Index (enumerate())
enumerate() ajoute un compteur aux itérables et le renvoie sous forme d'itérateur de tuples (index, valeur).
liste_elements = ['rouge', 'vert', 'bleu']
for index, couleur in enumerate(liste_elements):
print(f"Index {index} : {couleur}")
Évaluation d'Expressions (eval())
eval(expression_chaine) évalue une chaîne de caractères comme une expression Python. À utiliser avec prudence car elle peut exécuter du code arbitraire.
chaine_liste = '["item1", 123, "item2"]'
liste_evaluee = eval(chaine_liste)
print(f"Type après eval : {type(liste_evaluee)}, Contenu : {liste_evaluee}")
chaine_calcul = '10 * 5 + 2'
resultat_calcul = eval(chaine_calcul)
print(f"Résultat de l'évaluation : {resultat_calcul}, Type : {type(resultat_calcul)}")
Hachage (hash())
hash(objet) renvoie la valeur de hachage d'un objet. Seuls les objets immuables sont hachables (par exemple, nombres, chaînes, tuples). Les objets mutables (listes, dictionnaires) ne le sont pas.
print(f"Hachage de 100 : {hash(100)}")
print(f"Hachage de 'Python' : {hash('Python')}")
# print(hash([1, 2])) # Cela provoquerait une erreur TypeError
Vérification Logique (all() et any())
all(itérable) renvoie True si tous les éléments de l'itérable sont vrais (ou si l'itérable est vide). any(itérable) renvoie True si au moins un élément de l'itérable est vrai (ou False si l'itérable est vide).
print(f"all([1, 2, True]) : {all([1, 2, True])}")
print(f"all([1, 0, True]) : {all([1, 0, True])}")
print(f"all([]) : {all([])}")
print(f"any([0, False, '']) : {any([0, False, ''])}")
print(f"any([0, False, 'hello']) : {any([0, False, 'hello'])}")
print(f"any([]) : {any([])}")
Conversions de Base Numérique (bin(), oct(), hex())
Ces fonctions convertissent un nombre entier en sa représentation binaire, octale ou hexadécimale sous forme de chaîne.
nombre = 25
print(f"Binaire de {nombre} : {bin(nombre)}")
print(f"Octal de {nombre} : {oct(nombre)}")
print(f"Hexadécimal de {nombre} : {hex(nombre)}")
Répertorier les Attributs (dir())
dir(objet) renvoie la liste des noms des attributs et méthodes d'un objet (sans argument, il renvoie les noms dans le scope courant).
import math
print(dir(math))
# Cela affichera une longue liste d'attributs et de fonctions du module math, par exemple :
# ['__doc__', '__loader__', ..., 'acos', 'asin', 'ceil', 'cos', 'degrees', 'floor', 'log', 'pi', 'sqrt', ...]
- Introduction à la Programmation Procédurale
La programmation procédurale est un paradigme de programmation où les programmes sont construits à partir d'une séquence d'instructions, de fonctions ou de sous-routines. L'accent est mis sur l'ordre d'exécution des étapes pour atteindre un objectif.
Principes Clés
- Le programme est divisé en procédures (fonctions) qui effectuent des tâches spécifiques.
- Les données sont généralemnet séparées du code qui les manipule.
- Les procédures peuvent manipuler des données globales ou recevoir des données via des arguments.
- Le flux d'exécution est souvent séquentiel, avec des boucles et des conditions pour contrôler le chemin.
Avantages
- Simplicité pour les petits projets : Facile à comprendre et à mettre en œuvre pour des tâches simples ou des scripts.
- Flux clair : Le déroulement logique du programme est souvent facile à suivre étape par étape.
- Utilisation de la mémoire : Peut être plus efficace en termes de mémoire pour certaines applications.
Inconvénients
- Maintenance difficile : À mesure que le programme grandit, il devient difficile de gérer les dépendances entre les procédures et les données globales.
- Moins de réutilisabilité : Les procédures sont souvent fortement couplées aux données spécifiques qu'elles traitent, réduisant leur réutilisabilité.
- Difficulté d'extension : L'ajout de nouvelles fonctionnalités peut nécessiter des modifications importantes dans de nombreuses parties du code existant.
Exemple de Programmation Procédurale (Flux d'une commande simplifiée)
Dans cet exemple, une série de fonctions est appelée séquentiellement pour simuler un processus de commande simple : sélection de produits, affichage du panier, calcul du total et finalisation.
# Variables globales pour simuler un état partagé
panier_utilisateur = {}
solde_utilisateur = 100.0
def afficher_produits():
"""Affiche les produits disponibles avec leurs prix."""
produits_disponibles = {
'1': {'nom': 'Café', 'prix': 2.50},
'2': {'nom': 'Thé', 'prix': 2.00},
'3': {'nom': 'Jus', 'prix': 3.00}
}
print("\n--- Produits Disponibles ---")
for code, info in produits_disponibles.items():
print(f"{code}. {info['nom']} - {info['prix']:.2f} €")
return produits_disponibles
def ajouter_au_panier(produits):
"""Permet à l'utilisateur d'ajouter des produits au panier."""
global panier_utilisateur # Accès à la variable globale
while True:
choix_produit = input("Entrez le numéro du produit à ajouter (ou 'q' pour quitter) : ").strip()
if choix_produit == 'q':
break
if choix_produit in produits:
quantite_str = input(f"Combien de '{produits[choix_produit]['nom']}' voulez-vous ? ").strip()
if quantite_str.isdigit() and int(quantite_str) > 0:
quantite = int(quantite_str)
nom = produits[choix_produit]['nom']
prix_unitaire = produits[choix_produit]['prix']
if nom in panier_utilisateur:
panier_utilisateur[nom]['quantite'] += quantite
else:
panier_utilisateur[nom] = {'prix': prix_unitaire, 'quantite': quantite}
print(f"{quantite} {nom}(s) ajouté(s) au panier.")
else:
print("Quantité invalide.")
else:
print("Choix de produit invalide.")
def afficher_panier():
"""Affiche le contenu actuel du panier et le total."""
total_panier = 0.0
print("\n--- Votre Panier ---")
if not panier_utilisateur:
print("Votre panier est vide.")
return 0.0
for nom, details in panier_utilisateur.items():
prix_ligne = details['prix'] * details['quantite']
print(f"- {details['quantite']} x {nom} ({details['prix']:.2f} €/unité) = {prix_ligne:.2f} €")
total_panier += prix_ligne
print(f"--------------------")
print(f"Total : {total_panier:.2f} €")
return total_panier
def proceder_au_paiement(montant_total):
"""Gère le processus de paiement."""
global solde_utilisateur # Accès à la variable globale
if montant_total == 0:
print("Rien à payer.")
return
print(f"\nVotre solde actuel est de : {solde_utilisateur:.2f} €")
if solde_utilisateur >= montant_total:
confirmation = input(f"Confirmez-vous le paiement de {montant_total:.2f} € ? (oui/non) : ").strip().lower()
if confirmation == 'oui':
solde_utilisateur -= montant_total
print("Paiement effectué avec succès !")
print(f"Votre nouveau solde est de : {solde_utilisateur:.2f} €")
global panier_utilisateur # Réinitialiser le panier après achat
panier_utilisateur = {}
else:
print("Paiement annulé.")
else:
print("Solde insuffisant. Veuillez recharger votre compte.")
def demarrer_processus_commande():
"""Fonction principale orchestrant le processus de commande."""
produits = afficher_produits()
ajouter_au_panier(produits)
total_a_payer = afficher_panier()
if total_a_payer > 0:
proceder_au_paiement(total_a_payer)
else:
print("Processus de commande terminé sans achat.")
# Démarrage du programme
demarrer_processus_commande()
print("\nMerci d'avoir utilisé notre service !")