Comment ne rien faire en Python – Real Python

By | décembre 16, 2020

Formation gratuite Python

En Python, le passer le mot-clé est un entier déclaration en soi. Cette déclaration ne fait rien: elle est supprimée pendant la byte-compile phase. Mais pour une déclaration qui ne fait rien, le Python passer déclaration est étonnamment utile.

parfois passer est utile dans le code final qui s'exécute en production. Plus souvent, passer est utile comme échafaudage lors du développement de code. Dans des cas spécifiques, il existe de meilleures alternatives pour ne rien faire.

Python passer Déclaration: syntaxe et sémantique

Dans la syntaxe Python, les nouveaux blocs indentés suivent un caractère deux-points (:). Il y a plusieurs endroits où un nouveau bloc en retrait apparaîtra. Lorsque vous commencez à écrire du code Python, les emplacements les plus courants sont après le si mot-clé et après le pour mot-clé:

>>>

>>> pour X dans [[[[1, 2, 3]:
...     y = X + 1
...     impression(X, y)
...
1 2
2 3
3 4

Après le pour la déclaration est la corps du pour loop, qui se compose des deux lignes en retrait qui suivent immédiatement les deux points.

Dans ce cas, il y a deux instructions dans le corps qui sont répétées pour chaque valeur:

  1. y = x + 1
  2. imprimer (x, y)

Les instructions à l'intérieur de ce type de bloc sont techniquement appelées une suite dans la grammaire Python. Une suite doit inclure une ou plusieurs instructions. Il ne peut pas être vide.

Pour ne rien faire dans une suite, vous pouvez utiliser le spécial de Python passer déclaration. Cette instruction se compose d'un seul mot-clé passer. Alors que vous pouvez utiliser passer dans de nombreux endroits en Python, ce n'est pas toujours utile:

>>>

>>> si 1 + 1 == 2:
...     impression("les maths sont ok")
...     passer
...     impression("mais il faut s'y attendre")
...
les maths sont ok
mais c'est à prévoir

Dans ce si instruction, suppression de passer La déclaration garderait la même fonctionnalité et raccourcirait votre code. Vous vous demandez peut-être pourquoi la syntaxe Python inclut une instruction qui dit à l'interpréteur de ne rien faire. Ne pourriez-vous pas obtenir le même résultat en n’écrivant pas du tout de déclaration?

Dans certains cas, dire explicitement à Python de ne rien faire sert un objectif important. Par exemple, parce que le passer ne fait rien, vous pouvez l'utiliser pour répondre à l'exigence selon laquelle une suite comprend au moins une instruction:

>>>

>>> si 1 + 1 == 3:
...
  Fichier "", ligne 2

                ^
IndentationError: un bloc indenté attendu

Même si vous ne souhaitez pas ajouter de code dans le si bloc, un si block sans instruction crée une suite vide, ce qui est une syntaxe Python non valide.

Pour résoudre ce problème, vous pouvez utiliser passer:

>>>

>>> si 1 + 1 == 3:
...     passer
...

Maintenant, merci à passer, votre si est une syntaxe Python valide.

Utilisations temporaires de passer

Il existe de nombreuses situations dans lesquelles passer peut vous être utile pendant que vous développez, même s'il n'apparaîtra pas dans la version finale de votre code. Tout comme les échafaudages, passer peut être pratique pour maintenir la structure principale de votre programme avant de remplir les détails.

Cela peut sembler étrange d'écrire du code qui sera supprimé plus tard, mais faire les choses de cette façon peut accélérer votre développement initial.

Code futur

Il existe de nombreux cas où la structure du code nécessite, ou pourrait utiliser, un bloc. Bien que vous deviez éventuellement écrire du code là-bas, il est parfois difficile de sortir du flux de travail sur quelque chose de spécifique et de commencer à travailler sur une dépendance. Dans ces cas, un passer est un moyen utile de faire le minimum de travail pour la dépendance afin que vous puissiez revenir à ce sur quoi vous travailliez.

À titre d'exemple concret, imaginons écrire une fonction qui traite une chaîne, puis écrit le résultat dans un fichier et le renvoie:

def get_and_save_middle(Les données, fnom):
    milieu = Les données[[[[len(Les données)//3:2*len(Les données)//3]
    save_to_file(milieu, fnom)
    revenir milieu

Cette fonction enregistre et renvoie le tiers central d'une chaîne. Vous n'avez pas besoin de terminer la mise en œuvre save_to_file () avant de pouvoir tester la sortie pour une erreur hors-un-par-un. Toutefois, si save_to_file () n'existe pas sous une forme ou une autre, vous obtiendrez alors une erreur.

Il est possible de commenter l'appel à save_to_file (), mais n'oubliez pas de décommenter l'appel après avoir confirmé get_and_save_middle () fonctionne bien. Au lieu de cela, vous pouvez rapidement mettre en œuvre save_to_file () avec un passer déclaration:

def save_to_file(Les données, fnom):
    passer # TODO: remplissez-le plus tard

Cette fonction ne fait rien, mais elle vous permet de tester get_and_save_middle () sans fautes.

Un autre cas d'utilisation pour passer c'est lorsque vous écrivez une structure de contrôle de flux compliquée et que vous voulez un espace réservé pour le code futur. Lors de la mise en œuvre du défi fizz-buzz avec l'opérateur modulo, par exemple, il est utile de comprendre d'abord la structure du code:

si idx % 15 == 0:
    passer # Fizz-Buzz
elif idx % 3 == 0:
    passer # Fizz
elif idx % 5 == 0:
    passer # Buzz
autre:
    passer # Idx

Cette structure identifie ce qui doit être imprimé dans chaque cas, ce qui vous donne le squelette de la solution. Ces squelettes structurels sont utiles pour essayer de comprendre le logique de branchement dont si des déclarations sont nécessaires et dans quel ordre.

Par exemple, dans ce cas, une idée critique est que le premier si l'instruction doit vérifier la divisibilité par 15 parce que tout nombre qui est divisible par 15 serait également divisible par 5 et 3. Cet aperçu structurel est utile quels que soient les détails de la sortie spécifique.

Une fois que vous avez déterminé la logique de base du problème, vous pouvez décider si vous impression() directement dans le code:

def fizz_buzz(idx):
    si idx % 15 == 0:
        impression("fizz-buzz")
    elif idx % 3 == 0:
        impression("pétiller")
    elif idx % 5 == 0:
        impression("bourdonner")
    autre:
        impression(idx)

Cette fonction est simple à utiliser puisqu'elle imprime directement les chaînes. Cependant, ce n’est pas une fonction agréable à tester. Cela peut être un compromis utile. Cependant, lors des entretiens de codage, l'intervieweur vous demandera parfois d'écrire des tests. L'écriture de la structure vous permet d'abord de vous assurer que vous comprenez le flux logique avant de vérifier quelles sont les autres exigences.

Une alternative serait d'écrire une fonction qui renvoie la chaîne, puis de faire la boucle ailleurs:

def fizz_buzz(idx):
    si idx % 15 == 0:
        revenir "fizz-buzz"
    elif idx % 3 == 0:
        revenir "pétiller"
    elif idx % 5 == 0:
        revenir "bourdonner"
    autre:
        revenir str(idx)

Cette fonction pousse la fonctionnalité d'impression vers le haut de la pile et est plus facile à tester.

Déterminer les conditions fondamentales et la structure du problème en utilisant passer permet de décider plus facilement comment l'implémentation doit fonctionner ultérieurement.

Cette approche est également utile lors de l'écriture de classes. Si vous avez besoin d'écrire une classe pour implémenter quelque chose, mais que vous ne comprenez pas entièrement le domaine du problème, vous pouvez utiliser passer pour comprendre d'abord la meilleure disposition pour votre architecture de code.

Par exemple, imaginez que vous mettez en œuvre un Bonbons classe, mais les propriétés dont vous avez besoin ne sont pas évidentes. Finalement, vous devrez effectuer une analyse minutieuse des exigences, mais lors de la mise en œuvre des algorithmes de base, vous pouvez montrer clairement que la classe n'est pas encore prête:

Cela vous permet d'instancier les membres de la classe et de les transmettre sans avoir à décider quelles propriétés sont pertinentes pour la classe.

Marqueurs pour les débogueurs

Lorsque vous exécutez du code dans un débogueur, il est possible de définir un point d'arrêt dans le code où le débogueur s'arrêtera et vous permettra d'inspecter l'état du programme avant de continuer.

Lorsqu'un test déclenche souvent un point d'arrêt, par exemple dans une boucle, il peut y avoir de nombreuses instances où l'état du programme n'est pas intéressant. Pour résoudre ce problème, de nombreux débogueurs permettent également une point d'arrêt conditionnel, un point d'arrêt qui ne se déclenchera que lorsqu'une condition est vraie. Par exemple, vous pouvez définir un point d'arrêt dans un pour boucle qui n'est déclenchée que si une variable est Aucun pour voir pourquoi ce cas n’est pas traité correctement.

Cependant, de nombreux débogueurs vous permettent de définir uniquement quelques conditions de base sur vos points d'arrêt, telles que l'égalité ou peut-être une comparaison de taille. Vous pourriez avoir besoin d'une condition plus compliquée, telle que vérifier qu'une chaîne est un palindrome avant de rompre.

Bien que le débogueur puisse ne pas être capable de vérifier les palindromes, Python peut le faire avec un minimum d'effort. Vous pouvez profiter de cette fonctionnalité en ayant un ne rien faire si instruction et définition d'un point d'arrêt sur le passer ligne:

pour ligne dans filep:
    si ligne == ligne[::[::[::[::-1]:
        passer # Définissez le point d'arrêt ici
    processus(ligne)

En recherchant des palindromes avec ligne == ligne[::-1], vous avez maintenant une ligne qui ne s'exécute que si la condition est vraie.

Bien que le passer line ne fait rien, il vous permet d’y définir un point d’arrêt. Vous pouvez maintenant exécuter ce code dans un débogueur et interrompre uniquement les chaînes qui sont des palindromes.

Fonctions vides

Dans certains cas, il peut même être utile pour vous d'inclure une fonction vide dans la version déployée de votre code. Par exemple, une fonction dans une bibliothèque peut s'attendre à ce qu'une fonction de rappel soit transmise.

Un cas encore plus courant est celui où votre code définit une classe qui hérite d'une classe qui s'attend à ce qu'une méthode soit remplacée. Cependant, dans votre cas particulier, vous n’avez rien à faire. Ou peut-être que la raison pour laquelle vous remplacez le code est d'empêcher une méthode remplaçable de faire quoi que ce soit.

Dans tous ces cas, vous devrez écrire une fonction ou une méthode vide. Encore une fois, le problème est qu'il n'y a pas de lignes après le def la ligne n'est pas une syntaxe Python valide:

>>>

>>> def ignore_arguments(record, statut):
...
  Fichier "", ligne 2

                ^
IndentationError: un bloc indenté attendu

Cela échoue car une fonction, comme les autres blocs, doit inclure au moins une instruction. Pour résoudre ce problème, vous pouvez utiliser passer:

>>>

>>> def ignore_arguments(record, statut):
...     passer
...

Maintenant que la fonction a une instruction, même une qui ne fait rien, c'est une syntaxe Python valide.

Comme autre exemple, imaginez que vous ayez une fonction qui attend un objet semblable à un fichier dans lequel écrire. Cependant, vous souhaitez appeler la fonction pour une autre raison et souhaitez ignorer la sortie. Vous pouvez utiliser passer pour écrire une classe qui supprime toutes les données:

classe RejeterIO:
    def écrire(soi, Les données):
        passer

Les instances de cette classe prennent en charge .écrire() mais supprimez immédiatement toutes les données.

Dans ces deux exemples, il est important qu’une méthode ou une fonction existe, mais elle n’a rien à faire. Étant donné que les blocs Python doivent avoir des instructions, vous pouvez rendre les fonctions ou méthodes vides valides en utilisant passer.

Classes vides

En Python, l'héritage d'exceptions est important car il marque quelles exceptions sont interceptées. Par exemple, l'exception intégrée LookupError est un parent de KeyError. UNE KeyError Une exception est déclenchée lorsqu'une clé inexistante est recherchée dans un dictionnaire. Cela signifie que vous pouvez utiliser LookupError attraper un KeyError:

>>>

>>> vide=
>>> essayer:
...     vide[[[["une clé"]
... sauf LookupError comme exc:
...     impression("a obtenu une exception", repro(exc))
...
obtenu l'exception KeyError ('some key')
>>> isubclass(KeyError, LookupError)
Vrai

L'éxéption KeyError est attrapé même si le sauf déclaration précise LookupError. Ceci est dû au fait KeyError est une sous-classe de LookupError.

Parfois, vous souhaitez déclencher des exceptions spécifiques dans votre code, car elles ont un chemin de récupération spécifique. Cependant, vous voulez vous assurer que ces exceptions héritent d'une exception générale au cas où quelqu'un intercepterait l'exception générale. Ces classes d'exception n'ont ni comportement ni données. Ce ne sont que des marqueurs.

Afin de voir l'utilité d'une riche hiérarchie d'exceptions, vous pouvez envisager la vérification des règles de mot de passe. Avant d'essayer de changer le mot de passe sur un site Web, vous voulez le tester localement pour les règles qu'il applique:

  • Au moins huit caractères
  • Au moins un chiffre
  • Au moins un caractère spécial, tel qu'un point d'interrogation (?), un point d'exclamation (!), ou un point (.).

Chacune de ces erreurs doit avoir sa propre exception. Le code suivant implémente ces règles:

# password_checker.py
classe InvalidPasswordError(ValueError):
    passer

classe ShortPasswordError(InvalidPasswordError):
    passer

classe NoNumbersInPasswordError(InvalidPasswordError):
    passer

classe NoSpecialInPasswordError(InvalidPasswordError):
    passer

def check_password(mot de passe):
    si len(mot de passe) < 8:
        élever ShortPasswordError(mot de passe)
    pour n dans «0123456789»:
        si n dans mot de passe:
            Pause
    autre:
        élever NoNumbersInPasswordError(mot de passe)
    pour s dans "?!.":
        si s dans mot de passe:
            Pause
    autre:
        élever NoSpecialInPasswordError(mot de passe)

Cette fonction lèvera une exception si le mot de passe ne respecte pas les règles spécifiées. Un exemple plus réaliste noterait toutes les règles qui n'ont pas été suivies, mais cela dépasse le cadre de ce didacticiel.

Vous pouvez utiliser cette fonction dans un wrapper pour imprimer l'exception d'une manière agréable:

>>>

>>> de password_checker importer check_password
>>> def friendly_check(mot de passe):
...     essayer:
...         check_password(mot de passe)
...     sauf InvalidPasswordError comme exc:
...         impression("Mot de passe incorrect", repro(exc))
...
>>> friendly_check("Bonjour")
Mot de passe non valide ShortPasswordError ('bonjour')
>>> friendly_check("Bonjour le monde")
Mot de passe non valide NoNumbersInPasswordError ('helloworld')
>>> friendly_check("helloworld1")
Mot de passe non valide NoSpecialInPasswordError ('helloworld1')

Dans ce cas, friendly_check () captures seulement InvalidPasswordError depuis d'autres ValueError les exceptions sont probablement des bogues dans le vérificateur lui-même. Il imprime le nom et la valeur de l'exception, qui montre la règle qui n'a pas été suivie.

Dans certaines situations, vos utilisateurs peuvent ne pas se soucier exactement des problèmes existant dans l'entrée. Dans ce cas, vous voudriez juste attraper ValueError:

def get_username_and_password(identifiants):
    essayer:
        Nom, mot de passe = identifiants.Divisé(":", 1)
        check_password(mot de passe)
    sauf ValueError:
        revenir get_default_credentials()
    autre:
        revenir Nom, valeur

Dans ce code, toutes les entrées non valides sont traitées de la même manière car vous ne vous souciez pas des problèmes liés aux informations d'identification.

En raison de ces différents cas d'utilisation, check_password () a besoin des quatre exceptions:

  1. InvalidPasswordError
  2. ShortPasswordError
  3. NoNumbersPasswordError
  4. NoSpecialPasswordError

Chacune de ces exceptions décrit une règle différente violée. Dans le code qui compare une chaîne à des règles plus sophistiquées, il peut y en avoir beaucoup plus, disposées dans une structure complexe.

Malgré le besoin de quatre classes différentes, aucune des classes n'a de comportement. le passer L'instruction vous permet de définir rapidement les quatre classes.

Méthodes de marqueur

Certaines méthodes dans les classes n'existent pas pour être appelées mais pour marquer la classe comme étant associée d'une manière ou d'une autre à cette méthode.

La bibliothèque standard Python a le abc module. Le nom du module signifie classe de base abstraite. Ce module permet de définir des classes qui ne sont pas destinées à être instanciées mais servent plutôt de base commune à d’autres classes.

Si vous écrivez du code pour analyser les modèles d'utilisation d'un serveur Web, vous souhaiterez peut-être faire la différence entre les demandes provenant d'utilisateurs connectés et celles provenant de connexions non authentifiées. Vous pouvez modéliser cela en ayant un Origine superclasse qui a deux sous-classes: Connecté et Pas connecté.

Rien ne devrait jamais instancier le Origine classe directement. Chaque demande doit provenir d'un Connecté origine ou un Pas connecté origine. Voici une implémentation minimaliste:

importer abc


classe Origine(abc.abc):
    @abc.méthode abstraite
    def la description(soi):
        # Cette méthode ne sera jamais appelée
        passer


classe Pas connecté(Origine):
    def la description(soi):
        revenir "connexion non authentifiée"


classe Connecté(Origine):
    def la description(soi):
        revenir "connexion authentifiée"

Alors qu'un vrai Origine classe serait plus compliquée, cet exemple montre quelques-unes des bases. Origine.description () ne sera jamais appelée car toutes les sous-classes doivent la remplacer.

Car Origine a un méthode abstraite, il ne peut pas être instancié:

>>>

>>> Origine()
Traceback (dernier appel le plus récent):
  Fichier "", ligne 1, dans 
Erreur-type: Impossible d'instancier la classe abstraite Origin avec abstract ...
>>> connecté.la description()
'connexion authentifiée'
>>> pas connecté.la description()
'connexion non authentifiée'

Cours avec méthode abstraite les méthodes ne peuvent pas être instanciées. Cela signifie que tout objet qui a Origine en tant que superclasse sera une instance d'une classe qui remplace la description(). Pour cette raison, le corps en Origine.description () n'a pas d'importance, mais la méthode doit exister pour indiquer que toutes les sous-classes doivent l'instancier.

Parce que les corps de méthode ne peuvent pas être vides, vous devez mettre quelque chose dans Origine.description (). Encore une fois, la déclaration de ne rien faire passer est une bonne option pour indiquer clairement que vous avez inclus la ligne uniquement pour des raisons syntaxiques.

Une manière plus moderne d'indiquer que des méthodes sont nécessaires consiste à utiliser un Protocole, qui est disponible dans la bibliothèque standard de Python 3.8 et supérieur. Dans les anciennes versions de Python, il est disponible avec le typing_extensions backports.

UNE Protocole est différente d'une classe de base abstraite en ce qu'elle n'est pas explicitement associée à une classe concrète. Au lieu de cela, il s'appuie sur la correspondance de type pour l'associer au moment de la vérification de type avec mypy.

Les méthodes dans un Protocole ne sont jamais appelés. Ils ne servent qu'à marquer les types de méthodes nécessaires:

>>>

>>> de typing_extensions importer Protocole
>>> classe StringReader(Protocole):
...     def lis(soi, int) -> str:
...         passer

Démontrer comment utiliser un Protocole comme ça dans mypy n'est pas pertinent pour le passer déclaration. Mais ça est important de voir que le corps de la méthode n'a que passer déclaration.

Il existe d'autres exemples de tels marqueurs utilisés en dehors du langage Python et des bibliothèques standard. Par exemple, ils sont utilisés dans le zope.interface package pour indiquer les méthodes d'interface et dans automate pour indiquer les entrées d'un automate à états finis.

Dans tous ces cas, les classes doivent avoir des méthodes mais ne les appellent jamais. Pour cette raison, le corps n’a pas d’importance. Mais comme le corps ne peut pas être vide, vous pouvez utiliser le passer instruction pour ajouter un corps.

Alternatives à passer

le passer n'est pas le seul moyen de ne rien faire dans votre code. Ce n’est même pas le plus court, comme vous le verrez plus tard. Ce n’est même pas toujours l’approche la meilleure ou la plus pythonique.

Toute expression en Python est une instruction valide et chaque constante est une expression valide. Ainsi, les expressions suivantes ne font toutes rien:

  • Aucun
  • Vrai
  • 0
  • "bonjour je ne fais rien"

Vous pouvez utiliser l'une de ces expressions comme seule instruction dans une suite, et elle accomplira la même tâche que passer. La principale raison pour éviter de les utiliser comme des instructions ne rien faire est qu’elles sont unidiomatiques. Lorsque vous les utilisez, les personnes qui lisent votre code ne savent pas pourquoi elles sont là.

En général, le passer déclaration, tout en prenant plus de caractères à écrire que, disons, 0, est le meilleur moyen de communiquer aux futurs responsables de la maintenance que le bloc de code a été laissé vide intentionnellement.

Docstrings

Il existe une exception importante à l'idiome d'utilisation passer comme une déclaration de ne rien faire. Dans les classes, les fonctions et les méthodes, l'utilisation d'une expression de chaîne constante entraînera l'utilisation de l'expression comme objet .__ doc__ attribut.

le .__ doc__ l'attribut est utilisé par Aidez-moi() dans l'interpréteur interactif et par divers générateurs de documentation, de nombreux IDE et d'autres développeurs lisant le code. Certains styles de code insistent pour l'avoir dans chaque classe, fonction ou méthode.

Même lorsqu'une docstring n'est pas obligatoire, elle constitue souvent un bon substitut à la passer instruction dans un bloc vide. Vous pouvez modifier certains exemples du début de ce didacticiel pour utiliser une docstring au lieu de passer:

classe StringReader(Protocole):
      def lis(soi, longueur: int) -> str:
          "" "
                                        Lire une chaîne
                                        "" "

classe Origine(abc.abc):
    @abc.méthode abstraite
    def la description(soi):
        "" "
                                Description de l'origine lisible par l'homme
                                "" "

classe TropBeaucoupOpenParens(Erreur d'analyse):
    "" "
                Toutes les parenthèses ouvertes n'étaient pas fermées
                "" "

classe RejeterIO:
    def écrire(soi, Les données):
        "" "
                                Ignorer les données
                                "" "

Dans tous ces cas, la docstring rend le code plus clair. La docstring sera également visible lorsque vous utilisez ce code dans l'interpréteur interactif et dans les IDE, ce qui le rend encore plus précieux.

L'un des avantages techniques des docstrings, en particulier pour les fonctions ou méthodes qui ne s'exécutent jamais, est qu'elles ne sont pas marquées comme «découvertes» par les vérificateurs de couverture de test.

Ellipse

Dans les fichiers mypy stub, la méthode recommandée pour remplir un bloc est d'utiliser des points de suspension (...) comme expression constante. C'est une constante obscure qui évalue Ellipse:

>>>

>>> ...
Ellipse
>>> X = ...
>>> type(X), X
(, Ellipse)

le Ellipse objet singleton, du intégré ellipse class, est un objet réel produit par le ... expression.

L'utilisation originale pour Ellipse était dans la création de tranches multidimensionnelles. Cependant, c'est désormais la syntaxe recommandée pour remplir une suite dans un fichier stub:

# Dans un fichier `.pyi`:
def ajouter(une: int, b: int)-> int:
    ...

Cette fonction non seulement ne fait rien, mais elle est également dans un fichier que l’interpréteur Python n’évalue jamais.

Signaler une erreur

Dans les cas où les fonctions ou méthodes sont vides parce qu'elles ne s'exécutent jamais, parfois le meilleur corps pour elles est lever NotImplementedError ("cela ne devrait jamais arriver"). Bien que cela fasse techniquement quelque chose, cela reste une alternative valable à un passer déclaration.

Utilisations permanentes de passer

Parfois, l'utilisation du passer n'est pas temporaire – elle restera dans la version finale du code en cours d'exécution. Dans ces cas, il n’existe pas de meilleure alternative ou de langage plus courant pour remplir un bloc autrement vide que d’utiliser passer.

En utilisant passer dans la capture d'exceptions

Lors de l'utilisation essayez ... sauf pour intercepter une exception, vous n’avez parfois pas besoin de faire quoi que ce soit à propos de l’exception. Dans
cette situation, vous pouvez utiliser le passer déclaration pour faire taire l'erreur.

Si vous voulez vous assurer qu’un fichier n’existe pas, vous pouvez utiliser os.remove (). Cette fonction générera une erreur si le fichier n’y est pas. Cependant, le fichier ne s'y trouvant pas est exactement ce que vous voulez dans ce cas, l'erreur n'est donc pas nécessaire.

Voici une fonction qui supprime un fichier et n'échoue pas si le fichier n'existe pas:

importer os

def assurer_nonexistence(fnom):
    essayer:
        os.retirer(fnom)
    sauf FileNotFoundError:
        passer

Parce que rien ne doit être fait si un FileNotFoundError est soulevé, vous pouvez utiliser passer pour avoir un bloc sans autres instructions.

Notez que le passer l'instruction sera souvent remplacée par une instruction de journalisation. Cependant, il n'est pas nécessaire de le faire si l'erreur est attendue et bien comprise.

Dans ce cas, vous pouvez également utiliser le gestionnaire de contexte contextlib.suppress () pour supprimer l'erreur. Toutefois, si vous devez gérer certaines erreurs tout en ignorant d’autres, il est plus simple d’avoir un message vide sauf classe avec rien sauf le passer déclaration.

Par exemple, si vous vouliez avoir assurer_nonexistence () traiter les répertoires ainsi que les fichiers, vous pouvez alors utiliser cette approche:

importer os
importer shutil

def assurer_nonexistence(fnom):
    essayer:
       os.retirer(fnom)
    sauf FileNotFoundError:
       passer
    sauf IsADirectoryError:
       shutil.rmtree(fnom)

Ici, vous ignorez le FileNotFoundError tout en réessayant le IsADirectoryError.

Dans cet exemple, l'ordre des sauf les déclarations n’ont pas d’importance car FileNotFoundError et IsADirectoryError sont frères et sœurs et héritent tous deux de OSError. S'il y avait une affaire qui traitait le général OSError, peut-être en enregistrant et en l'ignorant, alors l'ordre importerait. Dans ce scénario, FileNotFoundError et son passer la déclaration devrait venir avant OSError.

En utilisant passer dans si ... elif Chaînes

Lorsque vous utilisez longtemps si ... elif chaînes, parfois vous n'avez rien à faire dans un cas. Cependant, vous ne pouvez pas ignorer cela elif parce que l'exécution continuerait jusqu'à l'autre condition.

Imaginez qu'un recruteur en ait assez d'utiliser le défi fizz-buzz comme question d'entretien et décide de le poser avec une touche. Cette fois, les règles sont un peu différentes:

  • Si le nombre est divisible par 20, imprimez "torsion".
  • Sinon, si le nombre est divisible par 15, n'imprimez rien.
  • Sinon, si le nombre est divisible par 5, alors imprimez "pétiller".
  • Sinon, si le nombre est divisible par 3, alors imprimez "bourdonner".
  • Sinon, imprimez le numéro.

L'intervieweur pense que cette nouvelle tournure rendra les réponses plus intéressantes.

Comme pour toutes les questions d'entrevue de codage, il existe de nombreuses façons de résoudre ce défi. Mais une façon est d'utiliser un pour boucle avec une chaîne qui imite la description ci-dessus:

pour X dans intervalle(100):
    si X % 20 == 0:
       impression("torsion")
    elif X % 15 == 0:
       passer
    elif X % 5 == 0:
       impression("pétiller")
    elif X % 3 == 0:
       impression("bourdonner")
    autre:
       impression(X)

le si ... elif La chaîne reflète la logique du passage à l'option suivante uniquement si la précédente n'a pas été prise.

Dans cet exemple, si vous avez supprimé le si x% 15 clause complètement, alors vous changeriez le comportement. Au lieu de ne rien imprimer pour les nombres divisibles par 15, vous imprimeriez "pétiller". La clause est essentielle même s’il n’ya rien à faire dans ce cas.

Ce cas d'utilisation pour le passer Cette instruction vous permet d'éviter de refactoriser la logique et de conserver le code organisé de manière à correspondre à la description du comportement.

Conclusion

Vous comprenez maintenant ce que le Python passer déclaration fait. Vous êtes prêt à l'utiliser pour améliorer votre vitesse de développement et de débogage, ainsi que pour le déployer avec tact dans votre code de production.

Dans ce didacticiel, vous avez appris:

  • Qu'est-ce que le Python passer déclaration est et pourquoi c'est utile
  • Comment utiliser le Python passer déclaration dans code de production
  • Comment utiliser le Python passer déclaration comme un aide tout en développant du code
  • Qu'est-ce que alternatives à passer sont et quand les utiliser

Vous pourrez désormais écrire du code meilleur et plus efficace en sachant comment dire à Python de ne rien faire.