Accès aux attributs et méthodes liées

PythonPythonBeginner
Pratiquer maintenant

This tutorial is from open-source community. Access the source code

💡 Ce tutoriel est traduit par l'IA à partir de la version anglaise. Pour voir la version originale, vous pouvez cliquer ici

Introduction

Dans ce labo, vous allez apprendre à accéder aux attributs en Python. Vous allez explorer comment utiliser des fonctions telles que getattr() et setattr() pour manipuler efficacement les attributs des objets.

De plus, vous allez expérimenter avec les méthodes liées (bound methods). Le labo vous guidera à travers ces concepts, et vous créerez un fichier nommé tableformat.py au cours du processus.

Ceci est un Guided Lab, qui fournit des instructions étape par étape pour vous aider à apprendre et à pratiquer. Suivez attentivement les instructions pour compléter chaque étape et acquérir une expérience pratique. Les données historiques montrent que c'est un laboratoire de niveau débutant avec un taux de réussite de 100%. Il a reçu un taux d'avis positifs de 100% de la part des apprenants.

Comprendre l'accès aux attributs en Python

En Python, les objets sont un concept fondamental. Ils peuvent stocker des données dans des attributs, qui sont comme des conteneurs nommés pour les valeurs. Vous pouvez considérer les attributs comme des variables appartenant à un objet. Il existe plusieurs façons d'accéder à ces attributs. La méthode la plus simple et la plus couramment utilisée est la notation pointée (.). Cependant, Python propose également des fonctions spécifiques qui vous offrent plus de flexibilité lors de la manipulation des attributs.

La notation pointée

Commençons par créer un objet Stock et voyons comment nous pouvons manipuler ses attributs à l'aide de la notation pointée. La notation pointée est un moyen simple et intuitif d'accéder et de modifier les attributs d'un objet.

Tout d'abord, ouvrez un nouveau terminal et lancez l'interpréteur interactif Python. C'est là que vous pouvez écrire et exécuter du code Python ligne par ligne.

## Open a new terminal and run Python interactive shell
python3

## Import the Stock class from the stock module
from stock import Stock

## Create a Stock object
s = Stock('GOOG', 100, 490.1)

## Get an attribute
print(s.name)    ## Output: 'GOOG'

## Set an attribute
s.shares = 50
print(s.shares)  ## Output: 50

## Delete an attribute
del s.shares
## If we try to access s.shares now, we'll get an AttributeError

Dans le code ci - dessus, nous importons d'abord la classe Stock du module stock. Ensuite, nous créons une instance de la classe Stock nommée s. Pour obtenir la valeur de l'attribut name, nous utilisons s.name. Pour modifier la valeur de l'attribut shares, nous assignons simplement une nouvelle valeur à s.shares. Et si nous voulons supprimer un attribut, nous utilisons le mot - clé del suivi du nom de l'attribut.

Fonctions d'accès aux attributs

Python fournit quatre fonctions intégrées très utiles pour la manipulation des attributs. Ces fonctions vous donnent plus de contrôle lors de la manipulation des attributs, en particulier lorsque vous devez les gérer de manière dynamique.

  1. getattr() - Cette fonction est utilisée pour obtenir la valeur d'un attribut.
  2. setattr() - Elle vous permet de définir la valeur d'un attribut.
  3. delattr() - Vous pouvez utiliser cette fonction pour supprimer un attribut.
  4. hasattr() - Cette fonction vérifie si un attribut existe dans un objet.

Voyons comment utiliser ces fonctions :

## Create a new Stock object
s = Stock('GOOG', 100, 490.1)

## Get an attribute
print(getattr(s, 'name'))       ## Output: 'GOOG'

## Set an attribute
setattr(s, 'shares', 50)
print(s.shares)                 ## Output: 50

## Check if an attribute exists
print(hasattr(s, 'name'))       ## Output: True
print(hasattr(s, 'symbol'))     ## Output: False

## Delete an attribute
delattr(s, 'shares')
print(hasattr(s, 'shares'))     ## Output: False

Ces fonctions sont particulièrement utiles lorsque vous devez travailler avec des attributs de manière dynamique. Au lieu d'utiliser des noms d'attributs codés en dur, vous pouvez utiliser des noms de variables. Par exemple, si vous avez une variable qui stocke le nom d'un attribut, vous pouvez passer cette variable à ces fonctions pour effectuer des opérations sur l'attribut correspondant. Cela vous offre plus de flexibilité dans votre code, en particulier lorsque vous travaillez avec différents objets et attributs de manière plus dynamique.

Utilisation de getattr() pour le traitement générique d'objets

La fonction getattr() est un outil puissant en Python qui vous permet d'accéder aux attributs d'un objet de manière dynamique. Cela est particulièrement utile lorsque vous souhaitez traiter des objets de manière générique. Au lieu d'écrire un code spécifique à un type d'objet particulier, vous pouvez utiliser getattr() pour travailler avec n'importe quel objet qui possède les attributs requis. Cette flexibilité rend votre code plus réutilisable et adaptable.

Traitement de plusieurs attributs

Commençons par apprendre à accéder à plusieurs attributs d'un objet à l'aide de la fonction getattr(). C'est un scénario courant lorsque vous avez besoin d'extraire des informations spécifiques d'un objet.

Tout d'abord, ouvrez l'interpréteur interactif Python si vous l'avez fermé précédemment. Vous pouvez le faire en exécutant la commande suivante dans votre terminal :

## Open a Python interactive shell if you closed the previous one
python3

Ensuite, nous allons importer la classe Stock et créer un objet Stock. La classe Stock représente une action avec des attributs tels que name, shares et price.

## Import the Stock class and create a stock object
from stock import Stock
s = Stock('GOOG', 100, 490.1)

Maintenant, nous allons définir une liste de noms d'attributs auxquels nous souhaitons accéder. Cette liste nous aidera à itérer sur les attributs et à afficher leurs valeurs.

## Define a list of attribute names
fields = ['name', 'shares', 'price']

Enfin, nous allons utiliser une boucle for pour itérer sur la liste de noms d'attributs et accéder à chaque attribut à l'aide de getattr(). Nous afficherons le nom de l'attribut et sa valeur à chaque itération.

## Access each attribute using getattr()
for name in fields:
    print(f"{name}: {getattr(s, 'name')}" if name == 'name' else f"{name}: {getattr(s, name)}")

Lorsque vous exécutez ce code, vous verrez la sortie suivante :

name: GOOG
shares: 100
price: 490.1

Cette sortie montre que nous avons pu accéder et afficher les valeurs de plusieurs attributs de l'objet Stock à l'aide de la fonction getattr().

Valeurs par défaut avec getattr()

La fonction getattr() offre également une fonctionnalité utile : la possibilité de spécifier une valeur par défaut si l'attribut auquel vous essayez d'accéder n'existe pas. Cela peut empêcher votre code de lever une erreur AttributeError et le rendre plus robuste.

Voyons comment cela fonctionne. Tout d'abord, nous allons essayer d'accéder à un attribut qui n'existe pas dans l'objet Stock. Nous utiliserons getattr() et fournirons une valeur par défaut de 'N/A'.

## Try to access an attribute that doesn't exist
print(getattr(s, 'symbol', 'N/A'))  ## Output: 'N/A'

Dans ce cas, puisque l'attribut symbol n'existe pas dans l'objet Stock, getattr() retourne la valeur par défaut 'N/A'.

Maintenant, comparons cela avec l'accès à un attribut existant. Nous allons accéder à l'attribut name, qui existe dans l'objet Stock.

## Compare with an existing attribute
print(getattr(s, 'name', 'N/A'))    ## Output: 'GOOG'

Ici, getattr() retourne la valeur réelle de l'attribut name, qui est 'GOOG'.

Traitement d'une collection d'objets

La fonction getattr() devient encore plus puissante lorsque vous avez besoin de traiter une collection d'objets. Voyons comment nous pouvons l'utiliser pour traiter un portefeuille d'actions.

Tout d'abord, nous allons importer la fonction read_portfolio du module stock. Cette fonction lit un portefeuille d'actions à partir d'un fichier CSV et retourne une liste d'objets Stock.

## Import the portfolio reading function
from stock import read_portfolio

Ensuite, nous allons utiliser la fonction read_portfolio pour lire le portefeuille à partir d'un fichier CSV nommé portfolio.csv.

## Read the portfolio from CSV file
portfolio = read_portfolio('portfolio.csv')

Enfin, nous allons utiliser une boucle for pour itérer sur la liste d'objets Stock dans le portefeuille. Pour chaque action, nous utiliserons getattr() pour accéder aux attributs name et shares et afficher leurs valeurs.

## Print the name and shares of each stock
for stock in portfolio:
    print(f"Stock: {getattr(stock, 'name')}, Shares: {getattr(stock, 'shares')}")

Cette approche rend votre code plus flexible car vous pouvez travailler avec les noms d'attributs sous forme de chaînes de caractères. Ces chaînes peuvent être passées en tant qu'arguments ou stockées dans des structures de données, vous permettant de changer facilement les attributs auxquels vous souhaitez accéder sans modifier la logique principale de votre code.

Création d'un formateur de table en utilisant l'accès aux attributs

En programmation, l'accès aux attributs est un concept fondamental qui nous permet d'interagir avec les propriétés des objets. Maintenant, nous allons mettre en pratique ce que nous avons appris sur l'accès aux attributs. Nous allons créer un utilitaire utile : un formateur de table. Ce formateur prendra une collection d'objets et les affichera sous forme de tableau, rendant les données plus faciles à lire et à comprendre.

Création du module tableformat.py

Tout d'abord, nous devons créer un nouveau fichier Python. Ce fichier contiendra le code de notre formateur de table.

Pour créer le fichier, suivez ces étapes :

  1. Dans l'IDE Web, cliquez sur le menu "File".
  2. Dans le menu déroulant, sélectionnez "New File".
  3. Enregistrez le fichier nouvellement créé sous le nom tableformat.py dans le répertoire /home/labex/project/.

Maintenant que nous avons notre fichier, écrivons le code de la fonction print_table() dans tableformat.py. Cette fonction sera chargée de formater et d'afficher nos objets sous forme de tableau.

def print_table(objects, fields):
    """
    Print a collection of objects as a formatted table.

    Args:
        objects: A sequence of objects
        fields: A list of attribute names
    """
    ## Print the header
    headers = fields
    for header in headers:
        print(f"{header:>10}", end=' ')
    print()

    ## Print the separator line
    for header in headers:
        print("-" * 10, end=' ')
    print()

    ## Print the data
    for obj in objects:
        for field in fields:
            value = getattr(obj, field)
            print(f"{value:>10}", end=' ')
        print()

Analysons ce que fait cette fonction :

  1. Elle prend deux arguments : une séquence d'objets et une liste de noms d'attributs. La séquence d'objets est les données que nous voulons afficher, et la liste de noms d'attributs indique à la fonction quelles propriétés des objets afficher.
  2. Elle affiche une ligne d'en-tête. La ligne d'en-tête contient les noms des attributs qui nous intéressent.
  3. Elle affiche une ligne de séparation. Cette ligne aide à séparer visuellement l'en-tête des données.
  4. Pour chaque objet de la séquence, elle affiche la valeur de chaque attribut spécifié. Elle utilise la fonction getattr() pour accéder à la valeur de l'attribut de chaque objet.

Maintenant, testons notre fonction print_table() pour voir si elle fonctionne comme prévu.

## Open a Python interactive shell
python3

## Import our modules
from stock import read_portfolio
import tableformat

## Read the portfolio data
portfolio = read_portfolio('portfolio.csv')

## Print the portfolio as a table with name, shares, and price columns
tableformat.print_table(portfolio, ['name', 'shares', 'price'])

Lorsque vous exécutez le code ci-dessus, vous devriez voir la sortie suivante :

      name     shares      price
---------- ---------- ----------
        AA        100       32.2
       IBM         50       91.1
       CAT        150      83.44
      MSFT        200      51.23
        GE         95      40.37
      MSFT         50       65.1
       IBM        100      70.44

L'un des grands avantages de notre fonction print_table() est sa flexibilité. Nous pouvons changer les colonnes affichées simplement en modifiant la liste fields.

## Just show shares and name
tableformat.print_table(portfolio, ['shares', 'name'])

L'exécution de ce code vous donnera la sortie suivante :

    shares       name
---------- ----------
       100         AA
        50        IBM
       150        CAT
       200       MSFT
        95         GE
        50       MSFT
       100        IBM

La force de cette approche réside dans sa généralité. Nous pouvons utiliser la même fonction print_table() pour afficher des tableaux pour n'importe quel type d'objet, tant que nous connaissons les noms des attributs que nous voulons afficher. Cela fait de notre formateur de table un outil très utile dans notre boîte à outils de programmation.

✨ Vérifier la solution et pratiquer

Comprendre les méthodes liées (bound methods) en Python

En Python, les méthodes sont un type spécial d'attributs que vous pouvez appeler. Lorsque vous accédez à une méthode via un objet, vous obtenez ce que l'on appelle une "méthode liée" (bound method). Une méthode liée est essentiellement une méthode qui est associée à un objet spécifique. Cela signifie qu'elle a accès aux données de l'objet et peut opérer sur elles.

Accéder aux méthodes en tant qu'attributs

Commençons à explorer les méthodes liées en utilisant notre classe Stock. Tout d'abord, voyons comment accéder à une méthode en tant qu'attribut d'un objet.

## Open a Python interactive shell
python3

## Import the Stock class and create a stock object
from stock import Stock
s = Stock('GOOG', 100, 490.10)

## Access the cost method without calling it
cost_method = s.cost
print(cost_method)  ## Output: <bound method Stock.cost of <stock.Stock object at 0x...>>

## Call the method
result = cost_method()
print(result)  ## Output: 49010.0

## You can also do this in one step
print(s.cost())  ## Output: 49010.0

Dans le code ci-dessus, nous importons d'abord la classe Stock et créons une instance de celle-ci. Ensuite, nous accédons à la méthode cost de l'objet s sans l'appeler réellement. Cela nous donne une méthode liée. Lorsque nous appelons cette méthode liée, elle calcule le coût en fonction des données de l'objet. Vous pouvez également appeler directement la méthode sur l'objet en une seule étape.

Utiliser getattr() avec les méthodes

Une autre façon d'accéder aux méthodes est d'utiliser la fonction getattr(). Cette fonction vous permet d'obtenir un attribut d'un objet par son nom.

## Get the cost method using getattr
cost_method = getattr(s, 'cost')
print(cost_method)  ## Output: <bound method Stock.cost of <stock.Stock object at 0x...>>

## Call the method
result = cost_method()
print(result)  ## Output: 49010.0

## Get and call in one step
result = getattr(s, 'cost')()
print(result)  ## Output: 49010.0

Ici, nous utilisons getattr() pour obtenir la méthode cost de l'objet s. Tout comme précédemment, nous pouvons appeler la méthode liée pour obtenir le résultat. Et vous pouvez même obtenir et appeler la méthode en une seule ligne.

La méthode liée et son objet

Une méthode liée garde toujours une référence à l'objet à partir duquel elle a été accédée. Cela signifie que même si vous stockez la méthode dans une variable, elle sait toujours à quel objet elle appartient et peut accéder aux données de cet objet.

## Store the cost method in a variable
c = s.cost

## Call the method
print(c())  ## Output: 49010.0

## Change the object's state
s.shares = 75

## Call the method again - it sees the updated state
print(c())  ## Output: 36757.5

Dans cet exemple, nous stockons la méthode cost dans une variable c. Lorsque nous appelons c(), elle calcule le coût en fonction des données actuelles de l'objet. Ensuite, nous changeons l'attribut shares de l'objet s. Lorsque nous appelons c() à nouveau, elle utilise les données mises à jour pour calculer le nouveau coût.

Explorer les internals de la méthode liée

Une méthode liée a deux attributs importants qui nous donnent plus d'informations sur elle.

  • __self__ : Cet attribut fait référence à l'objet auquel la méthode est liée.
  • __func__ : Cet attribut est l'objet fonction réel qui représente la méthode.
## Get the cost method
c = s.cost

## Examine the bound method attributes
print(c.__self__)  ## Output: <stock.Stock object at 0x...>
print(c.__func__)  ## Output: <function Stock.cost at 0x...>

## You can manually call the function with the object
print(c.__func__(c.__self__))  ## Output: 36757.5 (same as c())

Ici, nous accédons aux attributs __self__ et __func__ de la méthode liée c. Nous pouvons voir que __self__ est l'objet s, et __func__ est la fonction cost. Nous pouvons même appeler manuellement la fonction en passant l'objet en argument, et cela nous donne le même résultat qu'en appelant directement la méthode liée.

Exemple avec une méthode qui prend des arguments

Voyons comment les méthodes liées fonctionnent avec une méthode qui prend des arguments, comme la méthode sell().

## Get the sell method
sell_method = s.sell

## Examine the method
print(sell_method)  ## Output: <bound method Stock.sell of <stock.Stock object at 0x...>>

## Call the method with an argument
sell_method(25)
print(s.shares)  ## Output: 50

## Call the method manually using __func__ and __self__
sell_method.__func__(sell_method.__self__, 10)
print(s.shares)  ## Output: 40

Dans cet exemple, nous obtenons la méthode sell sous forme de méthode liée. Lorsque nous l'appelons avec un argument, elle met à jour l'attribut shares de l'objet s. Nous pouvons également appeler manuellement la méthode en utilisant les attributs __func__ et __self__, en passant également l'argument.

Comprendre les méthodes liées vous aide à comprendre le fonctionnement interne du système d'objets de Python, ce qui peut être utile pour le débogage, la métaprogrammation et la création de modèles de programmation avancés.

Résumé

Dans ce laboratoire, vous avez appris le système d'accès aux attributs de Python et ses mécanismes sous-jacents. Vous savez maintenant comment accéder aux attributs d'un objet en utilisant la notation pointée et des fonctions telles que getattr(), setattr(), delattr() et hasattr(). De plus, vous comprenez comment utiliser getattr() pour le traitement générique et flexible d'objets et comment créer un formateur de table pour toute collection d'objets.

Vous avez également saisi le concept des méthodes liées (bound methods) et comment elles maintiennent un lien avec leurs objets. Ces concepts fondamentaux sont essentiels pour les techniques de programmation avancées en Python telles que l'introspection, la réflexion et la métaprogrammation. Comprendre l'accès aux attributs vous permet d'écrire un code plus flexible et puissant capable de gérer différents types d'objets.