В Python, каковы плюсы и минусы реализации абстрактного метода с использованием статического метода? - PullRequest
2 голосов
/ 14 марта 2019

В Python, каковы плюсы и минусы реализации абстрактного метода с использованием статического метода?

Например,

import numpy as np


class ExponentialFamily:

    @abstractmethod
    def log_normalizer(self, q):
        raise NotImplementedError


class Multinomial(ExponentialFamily):

    @staticmethod
    def log_normalizer(q):
        max_q = np.maximum(0.0, np.amax(q))
        q_minus_max_q = q - max_q
        return max_q + np.logaddexp(-max_q, np.logaddexp.reduce(q_minus_max_q))

class NegativeBinomial(ExponentialFamily):

    def __init__(self, r):
        super().__init__()
        self.r = r

    def log_normalizer(self, q):
        return -self.r * np.log1p(-mf.exp(q))

С одной стороны, я знаю, что Пилинт будет меньше жаловаться на то, что self не используется. С другой стороны, кажется странным использовать статический метод здесь.

В ситуации кооперативного множественного наследования я не мог использовать staticmethod, потому что мне нужен хотя бы истинный тип для вызова super, а суперклассу может потребоваться объект self. Однако это не такая ситуация.

1 Ответ

4 голосов
/ 14 марта 2019

С точки зрения пуристического ООП, переопределение обычного метода статическим - это просто еретик .Но из-за того, как Python обрабатывает методы, это вполне допустимо языком.

Я попробую список pro / con:

Pros:

  • делает явным, что log_normalizer в Multinomial не зависит от экземпляра
  • сохраняет предупреждение Pylint

Минусы:

  • ООП, еретик.Пуристы будут кричать после того, как вы
  • тревожный дизайн для программистов, использующих не динамические языки, такие как C ++ или Java
  • необычный дизайн, что IMHO требует комментариев, объясняющих обоснование для будущих читателей / помощников
  • может быть следствием сомнительного дизайна: как метод может быть не статичным в базовом классе (аннотация не должна иметь значения) и статичным в подклассе
...