Cours Complet sur Python
Python est un langage de programmation populaire, reconnu pour sa simplicité, sa lisibilité et sa polyvalence. Il est utilisé dans de nombreux domaines, notamment le développement web, les scripts, le calcul scientifique et l’intelligence artificielle.
Présentation de Python
Python est un langage interprété, orienté objet et de haut niveau. Créé par Guido van Rossum, il est connu pour sa syntaxe simple et intuitive.
# Hello World en Python
print("Hello, World!")
Installation
Vous pouvez télécharger Python sur le site officiel : python.org. Une fois installé, ouvrez votre terminal ou ligne de commande et tapez :
python --version
Vous devriez voir la version de Python installée.
Variables et Types de Données
En Python, les variables sont utilisées pour stocker des informations ou des valeurs de différents types. Python propose plusieurs types de données natifs, dont les plus courants sont :
- Entiers (int) : pour les nombres entiers (ex :
10
) - Flottants (float) : pour les nombres décimaux (ex :
3.14
) - Chaînes de caractères (str) : pour les textes (ex :
"Python"
) - Booléens (bool) : pour les valeurs vraies ou fausses (ex :
True
ouFalse
)
Déclaration et Affectation de Variables
Déclarer une variable en Python est simple : il suffit d'utiliser un nom suivi d'un signe égal (=
) et de la valeur souhaitée.
# Exemples de variables
nombre = 10 # Variable entière
pi = 3.14 # Variable flottante
nom = "Python" # Variable chaîne de caractères
est_actif = True # Variable booléenne
Vous pouvez également afficher le type de chaque variable avec la fonction type()
:
# Vérifier le type de chaque variable
print(type(nombre)) #
print(type(pi)) #
print(type(nom)) #
print(type(est_actif)) #
Exemples Avancés : Manipulation des types de données
Conversions de types
Python permet de convertir un type de données en un autre. Voici quelques exemples de conversions :
# Conversion d'un entier en flottant
nombre = 10
flottant = float(nombre) # Devient 10.0
# Conversion d'un flottant en entier
flottant = 3.14
entier = int(flottant) # Devient 3
# Conversion d'un entier en chaîne de caractères
entier = 20
chaine = str(entier) # Devient "20"
# Conversion d'une chaîne de caractères en entier
chaine = "100"
entier = int(chaine) # Devient 100
Chaînes de Caractères : Manipulations et Opérations
Les chaînes de caractères (ou textes) peuvent être manipulées de différentes façons en Python :
# Exemple de manipulations de chaînes de caractères
message = "Bienvenue en Python!"
print(message.upper()) # Convertir en majuscules
print(message.lower()) # Convertir en minuscules
print(message.replace("Python", "la programmation")) # Remplacer un mot
Booléens et Opérations Logiques
Les booléens sont souvent utilisés pour contrôler des conditions logiques. Ils peuvent être combinés avec des opérateurs tels que and
, or
, et not
:
# Exemple d'opérations logiques
age = 20
est_majeur = age >= 18 # Retourne True
# Opérations logiques
est_etudiant = True
est_employe = False
resultat = est_etudiant or est_employe # Retourne True car l'une des conditions est vraie
1. Structure if-else
La structure conditionnelle if
permet d'exécuter un bloc de code uniquement si une condition est vraie.
L'instruction else
s'exécute dans le cas contraire.
Exemple : Vérifions si une personne est majeure ou mineure en fonction de son âge.
# Exemple de structure if-else
age = 20
if age >= 18:
print("Vous êtes majeur.")
else:
print("Vous êtes mineur.")
2. Structure if-elif-else
Utilisez elif
pour vérifier plusieurs conditions successives. Chaque bloc est vérifié dans l'ordre.
Cette structure est utile pour les décisions multi-options.
Exemple : Attribution d'une mention en fonction d'un score.
# Exemple de structure if-elif-else
score = 85
if score >= 90:
print("Mention Excellent")
elif score >= 70:
print("Mention Bien")
elif score >= 50:
print("Mention Passable")
else:
print("Mention Insuffisant")
3. Conditions Imbriquées
Les conditions imbriquées permettent de vérifier plusieurs critères dans différents niveaux de logique. Par exemple, on peut vérifier l'âge et le genre d'une personne pour afficher un message spécifique.
Exemple : Message spécifique en fonction de l'âge et du genre.
# Exemple de conditions imbriquées
age = 20
genre = "Femme"
if age >= 18:
if genre == "Femme":
print("Vous êtes une femme majeure.")
else:
print("Vous êtes un homme majeur.")
else:
print("Vous êtes mineur.")
Boucles
En Python, les boucles permettent de répéter une série d'instructions.
for
est souvent utilisé pour parcourir une séquence (comme une liste), tandis que while
continue tant qu'une condition est vraie.
Boucle for
La boucle for
permet de parcourir des séquences, comme des listes, des chaînes, ou des intervalles de nombres.
Exemple : Affichons chaque nombre de 0 à 4 en utilisant range
.
# Boucle for avec range
for i in range(5):
print(i)
Boucle while
La boucle while
continue tant qu'une condition est vraie. C'est utile pour des itérations où le nombre d'exécutions dépend d'une condition.
Exemple : Affichons les nombres de 0 à 4 en utilisant une boucle while
.
# Boucle while
compteur = 0
while compteur < 5:
print(compteur)
compteur += 1
Boucle for
avec une Liste
On peut utiliser une boucle for
pour parcourir directement les éléments d'une liste.
Exemple : Affichons chaque fruit dans une liste.
# Boucle for avec une liste
fruits = ["Pomme", "Banane", "Cerise"]
for fruit in fruits:
print(fruit)
Utilisation de break
et continue
break
termine une boucle prématurément, tandis que continue
passe directement à l'itération suivante.
Exemple : Utilisation de break
pour interrompre la boucle quand le nombre est égal à 3.
# Boucle avec break
for i in range(5):
if i == 3:
break
print(i)
Listes
Les listes sont des collections ordonnées et modifiables, qui permettent de stocker plusieurs éléments. Elles peuvent contenir des types de données variés et des éléments en double.
Création et Manipulation de Listes
Vous pouvez créer une liste en plaçant des éléments entre crochets []
et en les séparant par des virgules.
# Création d'une liste
fruits = ["pomme", "banane", "cerise"]
print(fruits)
Ajout d'Éléments
Utilisez append()
pour ajouter un élément à la fin de la liste ou insert()
pour ajouter un élément à une position spécifique.
fruits.append("orange") # Ajout à la fin
fruits.insert(1, "mangue") # Ajout à la position 1
print(fruits)
Accès aux Éléments
Les éléments de la liste sont accessibles en utilisant leur index, en commençant par 0 pour le premier élément.
premier_fruit = fruits[0] # Accès au premier élément
dernier_fruit = fruits[-1] # Accès au dernier élément
print(premier_fruit, dernier_fruit)
Modification d'Éléments
Vous pouvez modifier un élément en accédant à son index et en lui assignant une nouvelle valeur.
fruits[0] = "ananas" # Remplace "pomme" par "ananas"
print(fruits)
Suppression d'Éléments
Utilisez remove()
pour supprimer un élément spécifique, pop()
pour supprimer par index, ou clear()
pour vider la liste.
fruits.remove("banane") # Supprime "banane"
fruits.pop(2) # Supprime l'élément à l'index 2
print(fruits)
Parcourir une Liste
Utilisez une boucle for
pour itérer sur les éléments d'une liste.
for fruit in fruits:
print(fruit)
Listes Imbriquées
Les listes peuvent contenir d'autres listes, permettant de créer des structures multidimensionnelles.
# Liste imbriquée
fruits_et_legumes = [["pomme", "banane"], ["carotte", "épinard"]]
print(fruits_et_legumes[0][1]) # Accès à "banane"
Fonctions Utiles pour les Listes
len()
: retourne le nombre d'éléments dans la liste.sort()
: trie la liste en place.reverse()
: inverse l'ordre des éléments de la liste.
print(len(fruits)) # Longueur de la liste
fruits.sort() # Trie la liste
fruits.reverse() # Inverse la liste
print(fruits)
Fonctions Lambda
Les fonctions lambda sont des fonctions anonymes en Python, souvent utilisées pour des calculs simples, des opérations rapides, et en association avec d'autres fonctions comme map
, filter
, et sorted
.
Déclaration de Fonction Lambda
La syntaxe d’une fonction lambda consiste en le mot-clé lambda
suivi des paramètres, du symbole :
, et de l'expression à évaluer.
# Fonction lambda de base pour calculer le carré
carre = lambda x: x ** 2
print(carre(5)) # Affiche 25
Fonction Lambda avec Plusieurs Arguments
Les fonctions lambda peuvent accepter plusieurs arguments.
# Lambda avec deux arguments
addition = lambda x, y: x + y
print(addition(10, 5)) # Affiche 15
Utilisation avec map()
, filter()
, et sorted()
Les fonctions lambda sont souvent utilisées avec des fonctions intégrées pour manipuler des collections de données.
map()
avec Lambda
Applique la fonction à chaque élément d’une liste.
# Doubler chaque nombre dans la liste
nombres = [1, 2, 3, 4]
resultat = list(map(lambda x: x * 2, nombres))
print(resultat) # Affiche [2, 4, 6, 8]
filter()
avec Lambda
Filtre les éléments d'une liste selon une condition.
# Garder les nombres pairs
nombres = [1, 2, 3, 4, 5, 6]
pairs = list(filter(lambda x: x % 2 == 0, nombres))
print(pairs) # Affiche [2, 4, 6]
sorted()
avec Lambda
Tri des éléments selon une clé définie par lambda.
# Trier une liste de tuples par le deuxième élément
eleves = [("Alice", 15), ("Bob", 12), ("Charlie", 17)]
eleves_triees = sorted(eleves, key=lambda x: x[1])
print(eleves_triees) # Affiche [('Bob', 12), ('Alice', 15), ('Charlie', 17)]
Fonctions Lambda Imbriquées
Les lambdas peuvent aussi être utilisées comme éléments de retour de fonctions pour des calculs dynamiques.
# Fonction retournant une lambda
def create_multiplier(n):
return lambda x: x * n
doubler = create_multiplier(2)
tripler = create_multiplier(3)
print(doubler(5)) # Affiche 10
print(tripler(5)) # Affiche 15
Classes et Objets
Python est un langage orienté objet, et les classes permettent de structurer le code en utilisant des objets, qui sont des instances de classes. Cela permet de mieux organiser les données et les fonctionnalités associées.
Définition de Base d'une Classe
Une classe est un modèle définissant des propriétés (attributs) et des comportements (méthodes) pour ses objets.
# Définition de la classe Animal
class Animal:
def __init__(self, nom): # Constructeur de la classe
self.nom = nom # Attribut
def parler(self): # Méthode
print(f"{self.nom} fait du bruit.")
# Création d'une instance de la classe
chien = Animal("Chien")
chien.parler() # Affiche "Chien fait du bruit."
Attributs et Méthodes
Les attributs sont des variables associées à une classe, tandis que les méthodes sont des fonctions définies dans la classe pour agir sur les objets.
class Voiture:
def __init__(self, marque, annee):
self.marque = marque
self.annee = annee
def demarrer(self):
print(f"La {self.marque} démarre.")
def description(self):
print(f"Voiture : {self.marque}, Année : {self.annee}")
# Création d'un objet Voiture
ma_voiture = Voiture("Toyota", 2022)
ma_voiture.demarrer() # Affiche "La Toyota démarre."
ma_voiture.description() # Affiche "Voiture : Toyota, Année : 2022"
Héritage
L’héritage permet de créer une nouvelle classe basée sur une classe existante, permettant la réutilisation du code.
# Classe de base
class Animal:
def __init__(self, nom):
self.nom = nom
def parler(self):
print(f"{self.nom} fait un bruit.")
# Classe dérivée
class Chien(Animal):
def parler(self):
print(f"{self.nom} aboie.")
# Création d'une instance de Chien
rex = Chien("Rex")
rex.parler() # Affiche "Rex aboie."
Encapsulation
L'encapsulation est le processus de protection des données en rendant certains attributs privés. En Python, cela se fait en ajoutant un underscore (_
) ou un double underscore (__
) avant le nom de l'attribut.
class CompteBancaire:
def __init__(self, solde):
self.__solde = solde # Attribut privé
def deposer(self, montant):
self.__solde += montant
print(f"Dépôt de {montant}. Solde actuel : {self.__solde}")
def retirer(self, montant):
if montant <= self.__solde:
self.__solde -= montant
print(f"Retrait de {montant}. Solde actuel : {self.__solde}")
else:
print("Fonds insuffisants.")
compte = CompteBancaire(1000)
compte.deposer(500) # Affiche "Dépôt de 500. Solde actuel : 1500"
compte.retirer(200) # Affiche "Retrait de 200. Solde actuel : 1300"
Polymorphisme
Le polymorphisme permet d’utiliser une même méthode pour différents objets, offrant de la flexibilité dans le code.
class Chat:
def parler(self):
print("Miaou")
class Chien:
def parler(self):
print("Aboiement")
# Fonction qui accepte n'importe quel animal
def faire_parler(animal):
animal.parler()
# Utilisation du polymorphisme
chat = Chat()
chien = Chien()
faire_parler(chat) # Affiche "Miaou"
faire_parler(chien) # Affiche "Aboiement"
Les Exceptions
Les exceptions sont des erreurs qui surviennent pendant l'exécution du programme et interrompent son déroulement normal. La gestion des exceptions permet de capturer ces erreurs pour les traiter et éviter que le programme ne s'arrête brutalement.
Gestion de base des exceptions avec try
et except
Utilisez try
et except
pour intercepter les erreurs et exécuter un code alternatif.
# Exemple basique de gestion d'une exception
try:
resultat = 10 / 0
except ZeroDivisionError:
print("Erreur : Division par zéro impossible")
Gérer plusieurs types d'exceptions
Vous pouvez capturer plusieurs types d'exceptions en utilisant plusieurs blocs except
. Par exemple :
try:
valeur = int(input("Entrez un nombre : "))
resultat = 10 / valeur
except ValueError:
print("Erreur : Vous devez entrer un nombre valide.")
except ZeroDivisionError:
print("Erreur : Division par zéro impossible.")
Utilisation de else
et finally
Le bloc else
est exécuté si aucune exception n'est levée, tandis que le bloc finally
est toujours exécuté, que l'exception ait été levée ou non. Cela est utile pour les tâches de nettoyage.
try:
nombre = int(input("Entrez un nombre : "))
resultat = 100 / nombre
except ValueError:
print("Erreur : Entrez un nombre valide.")
except ZeroDivisionError:
print("Erreur : Division par zéro impossible.")
else:
print(f"Résultat : {resultat}")
finally:
print("Opération terminée.")
Lever des exceptions personnalisées avec raise
Il est possible de lever une exception manuellement en utilisant raise
, notamment pour valider les données ou conditions spécifiques.
def verifier_age(age):
if age < 18:
raise ValueError("L'âge doit être supérieur ou égal à 18.")
return "Âge accepté."
try:
age = int(input("Entrez votre âge : "))
print(verifier_age(age))
except ValueError as e:
print(f"Erreur : {e}")
Créer des exceptions personnalisées
Vous pouvez définir vos propres classes d'exceptions pour gérer des erreurs spécifiques de manière plus structurée. Par exemple :
# Définition d'une exception personnalisée
class SoldeInsuffisantError(Exception):
pass
def retirer_argent(solde, montant):
if montant > solde:
raise SoldeInsuffisantError("Le solde est insuffisant pour effectuer cette opération.")
return solde - montant
try:
solde = 100
montant = int(input("Montant à retirer : "))
nouveau_solde = retirer_argent(solde, montant)
print(f"Retrait effectué, nouveau solde : {nouveau_solde}")
except SoldeInsuffisantError as e:
print(f"Erreur : {e}")
Décorateurs
Les décorateurs sont des fonctions qui modifient ou enrichissent le comportement d’autres fonctions sans en changer le code. Ils sont souvent utilisés pour ajouter des fonctionnalités comme la journalisation, la vérification d’accès, ou la gestion du temps d’exécution d’une fonction.
Exemple de Décorateur Basique
Dans cet exemple, un décorateur affiche un message avant et après l’exécution de la fonction décorée :
# Définition d'un décorateur de base
def decorateur_simple(fonction):
def wrapper():
print("Avant la fonction")
fonction()
print("Après la fonction")
return wrapper
# Application du décorateur avec @
@decorateur_simple
def dire_bonjour():
print("Bonjour!")
# Appel de la fonction
dire_bonjour()
Décorateur avec Arguments
Les décorateurs peuvent aussi accepter des fonctions ayant des paramètres en ajoutant *args
et **kwargs
dans la fonction wrapper :
# Décorateur qui accepte des arguments de la fonction décorée
def decorateur_args(fonction):
def wrapper(*args, **kwargs):
print("Arguments:", args, kwargs)
return fonction(*args, **kwargs)
return wrapper
@decorateur_args
def addition(a, b):
return a + b
# Appel de la fonction avec des arguments
print("Résultat:", addition(3, 5))
Utilisation Pratique : Journalisation
Un décorateur peut être utile pour ajouter de la journalisation (log) à une fonction sans modifier son code :
import time
# Décorateur de journalisation
def journalisation(fonction):
def wrapper(*args, **kwargs):
print(f"Appel de la fonction '{fonction.__name__}' avec {args} et {kwargs}")
result = fonction(*args, **kwargs)
print(f"Résultat: {result}")
return result
return wrapper
@journalisation
def multiplier(x, y):
return x * y
# Appel de la fonction
multiplier(4, 6)
Exemple Avancé : Mesure du Temps d'Exécution
Les décorateurs sont souvent utilisés pour mesurer le temps d'exécution d'une fonction, pratique dans les cas où l’optimisation de la performance est importante :
# Décorateur pour mesurer le temps d'exécution
def temps_execution(fonction):
def wrapper(*args, **kwargs):
debut = time.time()
result = fonction(*args, **kwargs)
fin = time.time()
print(f"Temps d'exécution de {fonction.__name__}: {fin - debut} secondes")
return result
return wrapper
@temps_execution
def somme_lente(n):
total = 0
for i in range(n):
total += i
return total
# Appel de la fonction avec mesure du temps
somme_lente(1000000)
Remarque : Les décorateurs sont un puissant outil pour ajouter des fonctionnalités transversales (comme la journalisation, la vérification de permissions ou la gestion des exceptions) sans altérer le code d'origine des fonctions. Cela améliore la lisibilité et la réutilisabilité du code.