Обратите внимание, что Python изменил способ создания подклассов, поэтому есть два способа сделать это, и они не смешиваются. Вы получите ошибку, если смешаете. Прочтите этот пост, чтобы увидеть разницу: stackoverflow.com/questions/1713038/…
Марк Лаката
Ответы:
89
# Initialize using Parent#classMySubClass(MySuperClass):def__init__(self):
MySuperClass.__init__(self)
Или, что еще лучше, использование встроенной функции Pythonsuper() (см. Документацию Python 2 / Python 3 ) может быть немного лучшим методом вызова родительского элемента для инициализации:
# Better initialize using Parent (less redundant).#classMySubClassBetter(MySuperClass):def__init__(self):
super(MySubClassBetter, self).__init__()
Или то же самое, что и выше, за исключением использования формы с нулевым аргументом super(), которая работает только внутри определения класса:
Некоторые люди предостерегают от OTOH, superособенно для начинающих программистов на Python (например, Lutz). Я этого избегаю.
Эрик
6
Единственная причина, по которой следует избегать, super- это если вы не понимаете различий между тем, как superработает в Python, и как super/ parentработает на других языках. По общему признанию, это не очевидно для людей, пришедших с других языков, но я бы не стал делать вывод, что это квалифицирует это как нечто, от чего следует «предостеречь». Это действительно работает. Просто это работает иначе. Просто прочтите о том, что он на самом деле делает в Python, прежде чем пожаловаться на получение неожиданных результатов.
classSuperHero(object):#superclass, inherits from default objectdefgetName(self):raise NotImplementedError #you want to override this on the child classesclassSuperMan(SuperHero):#subclass, inherits from SuperHerodefgetName(self):return"Clark Kent"classSuperManII(SuperHero):#another subclassdefgetName(self):return"Clark Kent, Jr."if __name__ == "__main__":
sm = SuperMan()
print sm.getName()
sm2 = SuperManII()
print sm2.getName()
Вам нужно определить этот __init__метод только в том случае, если вы хотите добавить к нему дополнительный код, в противном случае исходный метод инициализации будет использоваться в любом случае (хотя об этом стоит упомянуть, и это совершенно действительный код)
dbr
2
Я думаю, вопрос был достаточно расплывчатым, чтобы предположить, что может быть добавлен дополнительный код. Лучше предоставить слишком много информации, чем недостаточно, и в конечном итоге возникнет другой вопрос, когда OP реализует его. :)
Круто. Это то, что я действительно искал, то есть подкласс без расширения / переопределения для суперпользователя.
BuvinJ
9
В приведенных выше ответах superинициализируется без каких-либо аргументов (ключевых слов). Однако часто вы хотите сделать это, а также передать некоторые собственные аргументы. Вот пример, иллюстрирующий этот вариант использования:
classSortedList(list):def__init__(self, *args, reverse=False, **kwargs):
super().__init__(*args, **kwargs) # Initialize the super class
self.reverse = reverse
self.sort(reverse=self.reverse) # Do additional things with the custom keyword arguments
Это подкласс, listкоторый при инициализации немедленно сортирует себя в направлении, указанном reverseаргументом ключевого слова, как показывают следующие тесты:
import pytest
deftest_1():assert SortedList([5, 2, 3]) == [2, 3, 5]
deftest_2():
SortedList([5, 2, 3], reverse=True) == [5, 3, 2]
deftest_3():with pytest.raises(TypeError):
sorted_list = SortedList([5, 2, 3], True) # This doesn't work because 'reverse' must be passed as a keyword argumentif __name__ == "__main__":
pytest.main([__file__])
Благодаря передаче *argsto superсписок может быть инициализирован и заполнен элементами, а не только пустым. (Обратите внимание, что reverseэто аргумент, содержащий только ключевое слово, в соответствии с PEP 3102 ).
Есть еще один способ динамически создавать подклассы в python с помощью функции type():
SubClass = type('SubClass', (BaseClass,), {'set_x': set_x}) # Methods can be set, including __init__()
Обычно вы хотите использовать этот метод при работе с метаклассами. Когда вы хотите выполнить автоматизацию более низкого уровня, это меняет способ создания классов в Python. Скорее всего, вам никогда не понадобится делать это таким образом, но когда вы это сделаете, вы уже будете знать, что делаете.
Этот ответ был бы более полезным, если бы вы включили объяснение того, что он делает
grooveplex
4
Хотя этот код может помочь решить проблему, он не объясняет, почему и / или как он отвечает на вопрос. Предоставление этого дополнительного контекста значительно улучшило бы его долгосрочную образовательную ценность. Пожалуйста , измените свой ответ , чтобы добавить объяснение, в том числе то , что применять ограничения и допущения.
Тоби Спейт
2
Хотя этот фрагмент кода может решить вопрос, включение объяснения действительно помогает улучшить качество вашего сообщения. Помните, что вы отвечаете на вопрос читателей в будущем, и эти люди могут не знать причины вашего предложения кода.
andreas
0
Создание подклассов в Python выполняется следующим образом:
Ответы:
# Initialize using Parent # class MySubClass(MySuperClass): def __init__(self): MySuperClass.__init__(self)
Или, что еще лучше, использование встроенной функции Python
super()
(см. Документацию Python 2 / Python 3 ) может быть немного лучшим методом вызова родительского элемента для инициализации:# Better initialize using Parent (less redundant). # class MySubClassBetter(MySuperClass): def __init__(self): super(MySubClassBetter, self).__init__()
Или то же самое, что и выше, за исключением использования формы с нулевым аргументом
super()
, которая работает только внутри определения класса:class MySubClassBetter(MySuperClass): def __init__(self): super().__init__()
источник
super
особенно для начинающих программистов на Python (например, Lutz). Я этого избегаю.super
- это если вы не понимаете различий между тем, какsuper
работает в Python, и какsuper
/parent
работает на других языках. По общему признанию, это не очевидно для людей, пришедших с других языков, но я бы не стал делать вывод, что это квалифицирует это как нечто, от чего следует «предостеречь». Это действительно работает. Просто это работает иначе. Просто прочтите о том, что он на самом деле делает в Python, прежде чем пожаловаться на получение неожиданных результатов.Маленький героический пример:
class SuperHero(object): #superclass, inherits from default object def getName(self): raise NotImplementedError #you want to override this on the child classes class SuperMan(SuperHero): #subclass, inherits from SuperHero def getName(self): return "Clark Kent" class SuperManII(SuperHero): #another subclass def getName(self): return "Clark Kent, Jr." if __name__ == "__main__": sm = SuperMan() print sm.getName() sm2 = SuperManII() print sm2.getName()
источник
class MySubClass(MySuperClass): def __init__(self): MySuperClass.__init__(self) # <the rest of your custom initialization code goes here>
Раздел о наследовании в документации питона объясняет это более подробно
источник
__init__
метод только в том случае, если вы хотите добавить к нему дополнительный код, в противном случае исходный метод инициализации будет использоваться в любом случае (хотя об этом стоит упомянуть, и это совершенно действительный код)class Class1(object): pass class Class2(Class1): pass
Class2 является подклассом Class1
источник
В приведенных выше ответах
super
инициализируется без каких-либо аргументов (ключевых слов). Однако часто вы хотите сделать это, а также передать некоторые собственные аргументы. Вот пример, иллюстрирующий этот вариант использования:class SortedList(list): def __init__(self, *args, reverse=False, **kwargs): super().__init__(*args, **kwargs) # Initialize the super class self.reverse = reverse self.sort(reverse=self.reverse) # Do additional things with the custom keyword arguments
Это подкласс,
list
который при инициализации немедленно сортирует себя в направлении, указанномreverse
аргументом ключевого слова, как показывают следующие тесты:import pytest def test_1(): assert SortedList([5, 2, 3]) == [2, 3, 5] def test_2(): SortedList([5, 2, 3], reverse=True) == [5, 3, 2] def test_3(): with pytest.raises(TypeError): sorted_list = SortedList([5, 2, 3], True) # This doesn't work because 'reverse' must be passed as a keyword argument if __name__ == "__main__": pytest.main([__file__])
Благодаря передаче
*args
tosuper
список может быть инициализирован и заполнен элементами, а не только пустым. (Обратите внимание, чтоreverse
это аргумент, содержащий только ключевое слово, в соответствии с PEP 3102 ).источник
Есть еще один способ динамически создавать подклассы в python с помощью функции
type()
:SubClass = type('SubClass', (BaseClass,), {'set_x': set_x}) # Methods can be set, including __init__()
Обычно вы хотите использовать этот метод при работе с метаклассами. Когда вы хотите выполнить автоматизацию более низкого уровня, это меняет способ создания классов в Python. Скорее всего, вам никогда не понадобится делать это таким образом, но когда вы это сделаете, вы уже будете знать, что делаете.
источник
class Subclass (SuperClass): # Subclass stuff here
источник
Ты используешь:
class DerivedClassName(BaseClassName):
Подробности см. В документации Python, раздел 9.5 .
источник
class Mammal(object): #mammal stuff class Dog(Mammal): #doggie stuff
источник
class BankAccount: def __init__(self, balance=0): self.balance = int(balance) def checkBalance(self): ## Checking opening balance.... return self.balance def deposit(self, deposit_amount=1000): ## takes in cash deposit amount and updates the balance accordingly. self.deposit_amount = deposit_amount self.balance += deposit_amount return self.balance def withdraw(self, withdraw_amount=500): ## takes in cash withdrawal amount and updates the balance accordingly if self.balance < withdraw_amount: ## if amount is greater than balance return `"invalid transaction"` return 'invalid transaction' else: self.balance -= withdraw_amount return self.balance class MinimumBalanceAccount(BankAccount): #subclass MinimumBalanceAccount of the BankAccount class def __init__(self,balance=0, minimum_balance=500): BankAccount.__init__(self, balance=0) self.minimum_balance = minimum_balance self.balance = balance - minimum_balance #print "Subclass MinimumBalanceAccount of the BankAccount class created!" def MinimumBalance(self): return self.minimum_balance c = BankAccount() print(c.deposit(50)) print(c.withdraw(10)) b = MinimumBalanceAccount(100, 50) print(b.deposit(50)) print(b.withdraw(10)) print(b.MinimumBalance())
источник
Создание подклассов в Python выполняется следующим образом:
class WindowElement: def print(self): pass class Button(WindowElement): def print(self): pass
Вот руководство по Python, которое также содержит классы и подклассы.
источник