Est-il conventionnel de déclencher une erreur NotImplementedError pour les méthodes dont l'implémentation est en attente, mais qui n'est pas prévue pour être abstraite?

34

J'aime soulever un NotImplementedErrorpour n'importe quelle méthode que je veux implémenter, mais où je n'ai pas encore réussi à le faire. J'ai peut-être déjà une implémentation partielle, mais ajoutez-la avec raise NotImplementedError()car je ne l'aime pas encore. D'un autre côté, j'aime aussi m'en tenir aux conventions, car cela facilitera la maintenance de mon code par d'autres personnes, et les conventions peuvent exister pour une bonne raison.

Cependant, la documentation Pythons pour NotImplementedError indique:

Cette exception est dérivée de RuntimeError. Dans les classes de base définies par l'utilisateur, les méthodes abstraites doivent déclencher cette exception lorsqu'elles nécessitent que les classes dérivées remplacent la méthode.

Il s'agit d'un cas d'utilisation formel beaucoup plus spécifique que celui que je décris. Est-ce un bon style conventionnel de soulever un NotImplementedErrorsimplement pour indiquer que cette partie de l'API est un travail en cours? Sinon, existe-t-il une autre manière standardisée de l'indiquer?

gerrit
la source
Qu'entendez-vous par «approprié»?
Robert Harvey
1
@RobertHarvey Je suppose que je veux dire conventionnel, suivant une utilisation courante. J'ai reformulé ma question maintenant.
gerrit
1
Nous utilisons C # ici principalement, mais ce type de levée d'exception est idiomatique ici, et je m'attendrais ailleurs. Casser tôt et briser fort est une bonne ligne directrice pour identifier rapidement les problèmes potentiels (lire: à peu de frais).
Telastyn
Généralement, si je crée une classe, je mets simplement les commentaires TODO dans des méthodes non implémentées jusqu'à ce que j'arrive à implémenter la fonctionnalité. Si la classe devait être mise en production avant que cela ne se produise, j'envisagerais de lever des exceptions.
5
Pour ce que ça vaut, c'est ce que Microsoft Visual Studio fait par défaut lorsque vous utilisez l'IDE pour «implémenter une interface». Chez Robert Harvey, le résultat est bien compris.
catfood

Réponses:

34

Il convient de noter que, si la documentation Python fournit un cas d'utilisation (et probablement canonique) pour cette exception, elle n'exclut pas spécifiquement son utilisation dans d'autres scénarios.

Je considérerais approprié de déclencher une exception NotImplementedError si vous n'avez pas encore remplacé une méthode dans une classe de base (pour satisfaire l '"interface").

Une vérification rapide sur Google suggère que les gens comprendront ce que vous voulez dire si vous utilisez l'exception de cette manière. Il n'y a aucun effet secondaire ou conséquence involontaire à ma connaissance; la méthode lèvera simplement une exception si elle est appelée, et elle lèvera une exception bien comprise par tout le monde.


La documentation de Python 3 reflète cette utilisation exacte:

Dans les classes de base définies par l'utilisateur, les méthodes abstraites doivent déclencher cette exception lorsqu'elles nécessitent que les classes dérivées remplacent la méthode ou lorsque la classe est en cours de développement pour indiquer que l'implémentation réelle doit encore être ajoutée . [Italiques ajoutés]

Robert Harvey
la source
+1, mais j'ajouterais également que pour ce type de convention, un peu de documentation peut aller très loin. Comme une note d'une ligne dans un wiki de développement, un fichier Lisezmoi de référentiel ou une directive de style - quelque chose comme ça - expliquant pourquoi vous utilisez cette exception.
Ben Lee
8

Cela sera compris, que vous le fassiez ou non, cela devrait dépendre des conventions locales (équipe ou entreprise). Notez que cela a moins de sens dans le contexte de TDD car le TEST devrait être ce qui détermine que la méthode n'est pas implémentée.

La version courte est: à utiliser si vous et votre équipe le jugez approprié.

jmoreno
la source
5
FWIW, Lancer l'exception devrait être un bon moyen de faire échouer le test, si pour une raison quelconque vous devez forcer ce comportement. (Il serait utile dans le cadre d'un stub intellisense de définition de méthode, par exemple.)
DougM
1

Il semble que cela NotImplementedErrorsoit généralement soulevé pour les développements de fonctionnalités Python lui-même, comme suit:

@classmethod
def fromkeys(cls, iterable, v=None):
    # There is no equivalent method for counters because setting v=1
    # means that no element can have a count greater than one.
    raise NotImplementedError(
        'Counter.fromkeys() is undefined.  Use Counter(iterable) instead.')

Documetation

fromkeys (itérable)

Cette méthode de classe n'est pas implémentée pour les objets Counter.

La source

Collections.Counter.fromkeys

Emma
la source