@@ -178,27 +178,35 @@ override has a compatible signature:
178178
179179.. code-block :: python
180180
181- class A :
181+ class Base :
182182 def f (self , x : int ) -> None :
183183 ...
184184
185- class B ( A ):
185+ class Derived1 ( Base ):
186186 def f (self , x : str ) -> None : # Error: type of 'x' incompatible
187187 ...
188188
189- class C ( A ):
189+ class Derived2 ( Base ):
190190 def f (self , x : int , y : int ) -> None : # Error: too many arguments
191191 ...
192192
193- class D ( A ):
193+ class Derived3 ( Base ):
194194 def f (self , x : int ) -> None : # OK
195195 ...
196196
197+ class Derived4 (Base ):
198+ def f (self , x : float ) -> None : # OK: mypy treats int as a subtype of float
199+ ...
200+
201+ class Derived5 (Base ):
202+ def f (self , x : int , y : int = 0 ) -> None : # OK: accepts more than the base
203+ ... # class method
204+
197205 .. note ::
198206
199207 You can also vary return types **covariantly ** in overriding. For
200- example, you could override the return type ``object `` with a subtype
201- such as ``int ``. Similarly, you can vary argument types
208+ example, you could override the return type ``Iterable[int] `` with a
209+ subtype such as ``List[ int] ``. Similarly, you can vary argument types
202210 **contravariantly ** -- subclasses can have more general argument types.
203211
204212You can also override a statically typed method with a dynamically
@@ -213,50 +221,103 @@ effect at runtime:
213221
214222.. code-block :: python
215223
216- class A :
224+ class Base :
217225 def inc (self , x : int ) -> int :
218226 return x + 1
219227
220- class B ( A ):
228+ class Derived ( Base ):
221229 def inc (self , x ): # Override, dynamically typed
222- return ' hello' # Incompatible with 'A ', but no mypy error
230+ return ' hello' # Incompatible with 'Base ', but no mypy error
223231
224232 Abstract base classes and multiple inheritance
225233**********************************************
226234
227235Mypy supports Python abstract base classes (ABCs). Abstract classes
228236have at least one abstract method or property that must be implemented
229- by a subclass. You can define abstract base classes using the
230- ``abc.ABCMeta `` metaclass, and the ``abc.abstractmethod `` and
231- `` abc.abstractproperty `` function decorators . Example:
237+ by any * concrete * (non-abstract) subclass. You can define abstract base
238+ classes using the ``abc.ABCMeta `` metaclass and the ``abc.abstractmethod ``
239+ function decorator . Example:
232240
233241.. code-block :: python
234242
235243 from abc import ABCMeta, abstractmethod
236244
237- class A (metaclass = ABCMeta ):
245+ class Animal (metaclass = ABCMeta ):
238246 @abstractmethod
239- def foo (self , x : int ) -> None : pass
247+ def eat (self , food : str ) -> None : pass
240248
249+ @ property
241250 @abstractmethod
242- def bar (self ) -> str : pass
251+ def can_walk (self ) -> bool : pass
252+
253+ class Cat (Animal ):
254+ def eat (self , food : str ) -> None :
255+ ... # Body omitted
243256
244- class B (A ):
245- def foo (self , x : int ) -> None : ...
246- def bar (self ) -> str :
247- return ' x'
257+ @ property
258+ def can_walk (self ) -> bool :
259+ return True
248260
249- a = A() # Error: 'A' is abstract
250- b = B() # OK
261+ x = Animal() # Error: 'Animal' is abstract due to 'eat' and 'can_walk'
262+ y = Cat() # OK
263+
264+ .. note ::
265+
266+ In Python 2.7 you have to use ``@abc.abstractproperty `` to define
267+ an abstract property.
251268
252269Note that mypy performs checking for unimplemented abstract methods
253270even if you omit the ``ABCMeta `` metaclass. This can be useful if the
254271metaclass would cause runtime metaclass conflicts.
255272
273+ Since you can't create instances of ABCs, they are most commonly used in
274+ type annotations. For example, this method accepts arbitrary iterables
275+ containing arbitrary animals (instances of concrete ``Animal ``
276+ subclasses):
277+
278+ .. code-block :: python
279+
280+ def feed_all (animals : Iterable[Animal], food : str ) -> None :
281+ for animal in animals:
282+ animal.eat(food)
283+
284+ There is one important peculiarity about how ABCs work in Python --
285+ whether a particular class is abstract or not is somewhat implicit.
286+ In the example below, ``Derived `` is treated as an abstract base class
287+ since ``Derived `` inherits an abstract ``f `` method from ``Base `` and
288+ doesn't explicitly implement it. The definition of ``Derived ``
289+ generates no errors from mypy, since it's a valid ABC:
290+
291+ .. code-block :: python
292+
293+ from abc import ABCMeta, abstractmethod
294+
295+ class Base (metaclass = ABCMeta ):
296+ @abstractmethod
297+ def f (self , x : int ) -> None : pass
298+
299+ class Derived (Base ): # No error -- Derived is implicitly abstract
300+ def g (self ) -> None :
301+ ...
302+
303+ Attempting to create an instance of ``Derived `` will be rejected,
304+ however:
305+
306+ .. code-block :: python
307+
308+ d = Derived() # Error: 'Derived' is abstract
309+
310+ .. note ::
311+
312+ It's a common error to forget to implement an abstract method.
313+ As shown above, the class definition will not generate an error
314+ in this case, but any attempt to construct an instance will be
315+ flagged as an error.
316+
256317A class can inherit any number of classes, both abstract and
257318concrete. As with normal overrides, a dynamically typed method can
258- implement a statically typed method defined in any base class,
259- including an abstract method defined in an abstract base class.
319+ override or implement a statically typed method defined in any base
320+ class, including an abstract method defined in an abstract base class.
260321
261322You can implement an abstract property using either a normal
262323property or an instance variable.
0 commit comments