An abstract method is one that you're supposed to implement yourself, if you inherit from any of these classes. For example:
class MyIter(collections.abc.Iterator):
# We must override __next__ because it's abstract in `Iterator`.
def __next__(self):
...
A mixin is a method whose implementation is already provided in the superclass. So you don't need to override __iter__, because Iterator already implements it.
To continue with the Iterator example: the Iterator class itself is implemented like this (slightly simplified):
class Iterator(Iterable):
@abc.abstractmethod
def __next__(self):
pass
def __iter__(self):
return self
We're using abc.abstractmethod to indicate that __next__ is abstract; if you forget to override it in your concrete implementation class, the decorator will cause an exception to be raised.
The __iter__ method, on the other hand, has an implementation that simply returns self, as expected from iterator objects.