Coder Perfect

What is a mixin, and why do you need one?

Problem

Mark Lutz describes “mixins” in his book “Programming Python.” I’m a C/C++/C# programmer who has never heard of the term. What exactly is a mixin?

Reading between the lines of this example (which I’ve linked to because it’s pretty long), it appears that multiple inheritance is being used to extend a class rather than ‘real’ subclassing. Is this correct?

Why would I want to do that rather than create a subclass for the new functionality? Why would utilizing composition be preferable to using a mixin/multiple inheritance approach?

What separates a mixin from multiple inheritance? Is it just a matter of semantics?

Asked by TarkaDaal

Solution #1

A mixin is a type of multiple inheritance that is unique. Mixins are typically employed in one of two scenarios:

Consider werkzeug’s request and response mechanism as an example of number one. I can create a basic request object by typing:

from werkzeug import BaseRequest

class Request(BaseRequest):
    pass

If I wanted to add support for accept headers, I’d do so.

from werkzeug import BaseRequest, AcceptMixin

class Request(AcceptMixin, BaseRequest):
    pass

I could do the following to create a request object that supports accept headers, etags, authentication, and user agent support:

from werkzeug import BaseRequest, AcceptMixin, ETagRequestMixin, UserAgentMixin, AuthenticationMixin

class Request(AcceptMixin, ETagRequestMixin, UserAgentMixin, AuthenticationMixin, BaseRequest):
    pass

The distinction is slight, but the mixin classes in the preceding instances were not designed to stand on their own. AuthenticationMixin (for example) would probably be something like Authenticator in more classic multiple inheritance. That is, the class would most likely be designed to function independently.

Answered by Jason Baker

Solution #2

To begin, you should be aware that mixins are only available in languages with multiple inheritance. A mixin is not possible in Java or C#.

A mixin is a stand-alone base type for a child class that provides restricted functionality and polymorphic resonance. If you’re thinking in C#, consider an interface that you don’t have to create since it already exists; you simply inherit from it and get the benefits of its functionality.

Mixins are usually limited in scope and are not intended to be extended.

[edit โ€” to clarify:]

Since you asked, I suppose I should explain why. The main advantage is that you will not have to repeat the process. The Disposal pattern in C# may be the most important place where a mixin might help. You nearly always want to follow the same pattern while implementing IDisposable, yet you end up writing and re-writing the same fundamental code with slight differences. You could save a lot of typing time if there was an extensible Disposal mixin.

[edit 2 โ€” to respond to your other inquiries]

Yes. The distinction between a mixin and ordinary multiple inheritance is purely semantic; a class with multiple inheritance might use a mixin as part of that inheritance.

A mixin is a type that may be “mixed in” to any other type via inheritance without changing the inherited type while still providing useful functionality to that type.

Consider an interface that has already been implemented.

I don’t utilize mixins because I create in a language that doesn’t support them, thus I’m having a hard time coming up with a good example that will simply provide you with that “aha!” moment. But I’ll give it another shot. I’ll use a contrived example โ€” most languages already have the functionality in some form or another โ€” but it should demonstrate how mixins are designed to be produced and utilized. Here’s how it goes:

Let’s say you have a type that needs to be serialized to and from XML. You want the type to have two methods: “ToXML,” which returns a string containing an XML fragment containing the type’s data values, and “FromXML,” which allows the type to reconstruct its data values from an XML fragment in a string. Again, this is a made-up example; you could use a file stream, an XML Writer class from your language’s runtime library, or whatever you choose. The concept is that you want to serialize your object to XML and then retrieve a new object from it.

The other important point in this example is that you want to do this in a generic way. You don’t want to have to implement a “ToXML” and “FromXML” method for every type that you want to serialize, you want some generic means of ensuring that your type will do this and it just works. You want code reuse.

You could develop the XmlSerializable mixin to do your work for you if your language supported it. The ToXML and FromXML methods would be implemented by this type. It would be capable of obtaining the essential data from any type that it is mixed in with to produce the XML fragment returned by ToXML, and it would be equally capable of restoring that data when FromXML is called, using some mechanism that isn’t important to the example.

That’s all there is to it. Any type that has to be serialized to XML should inherit from XmlSerializable to use it. You would just call ToXML or FromXML whenever you needed to serialize or deserialize that type. In reality, because XmlSerializable is a full-fledged type with polymorphism, you could make a document serializer that doesn’t know anything about your original type and only accepts an array of XmlSerializable types.

Consider how you could use this scenario to create a mixin that assures that every class that uses it logs every method call, or a mixin that gives transactionality to the type that uses it. The list could go on indefinitely.

If you conceive of a mixin as a little base type that adds a small amount of functionality to a type without changing it in any way, you’ll be OK.

Hopefully. ๐Ÿ™‚

Answered by Randolpho

Solution #3

This answer seeks to explain mixins using the following examples:

It will also address the contentious issue of:

Definitions

I have yet to come across a citation from a “authoritative” source that defines a mixin in Python.

I’ve seen two alternative definitions of a mixin (if they’re to be distinguished from other related ideas like abstract base classes), and no one seems to know which one is true.

Various languages may have different levels of agreement.

No multiple inheritance (definition 1)

A mixin is a class in which one of its methods calls a method that isn’t declared in the class.

It is not intended to be instantiated, but rather to act as a foundation class. Otherwise, the instance’s methods would not be able to be invoked without throwing an exception.

A constraint which some sources add is that the class may not contain data, only methods, but I don’t see why this is necessary. In practice however, many useful mixins don’t have any data, and base classes without data are simpler to use.

The implementation of all comparison operators using only the operators = and == is a classic example:

class ComparableMixin(object):
    """This class has methods which use `<=` and `==`,
    but this class does NOT implement those methods."""
    def __ne__(self, other):
        return not (self == other)
    def __lt__(self, other):
        return self <= other and (self != other)
    def __gt__(self, other):
        return not self <= other
    def __ge__(self, other):
        return self == other or self > other

class Integer(ComparableMixin):
    def __init__(self, i):
        self.i = i
    def __le__(self, other):
        return self.i <= other.i
    def __eq__(self, other):
        return self.i == other.i

assert Integer(0) <  Integer(1)
assert Integer(0) != Integer(1)
assert Integer(1) >  Integer(0)
assert Integer(1) >= Integer(1)

# It is possible to instantiate a mixin:
o = ComparableMixin()
# but one of its methods raise an exception:
#o != o 

The functools.total ordering() decorator might have been used for this example, but the goal was to reinvent the wheel:

import functools

@functools.total_ordering
class Integer(object):
    def __init__(self, i):
        self.i = i
    def __le__(self, other):
        return self.i <= other.i
    def __eq__(self, other):
        return self.i == other.i

assert Integer(0) < Integer(1)
assert Integer(0) != Integer(1)
assert Integer(1) > Integer(0)
assert Integer(1) >= Integer(1)

Multiple inheritance (definition 2)

A mixin is a design pattern in which a base class’s method calls a method that it doesn’t define, and that method is intended to be implemented by another base class rather than the derived, as in Definition 1.

Mixin classes are base classes that are intended to be used in that design pattern (TODO those who use the method, or those who implement it?)

It’s not always clear whether a class is a mixin: the function could just be implemented on the derived class, in which case we’re back at Definition 1. You must think about the author’s intentions.

This method is appealing because it allows for the recombination of capabilities using several base classes:

class HasMethod1(object):
    def method(self):
        return 1

class HasMethod2(object):
    def method(self):
        return 2

class UsesMethod10(object):
    def usesMethod(self):
        return self.method() + 10

class UsesMethod20(object):
    def usesMethod(self):
        return self.method() + 20

class C1_10(HasMethod1, UsesMethod10): pass
class C1_20(HasMethod1, UsesMethod20): pass
class C2_10(HasMethod2, UsesMethod10): pass
class C2_20(HasMethod2, UsesMethod20): pass

assert C1_10().usesMethod() == 11
assert C1_20().usesMethod() == 21
assert C2_10().usesMethod() == 12
assert C2_20().usesMethod() == 22

# Nothing prevents implementing the method
# on the base class like in Definition 1:

class C3_10(UsesMethod10):
    def method(self):
        return 3

assert C3_10().usesMethod() == 13

Authoritative Python occurrences

The phrase Mixin Methods is used directly in the official documentation for collections.abc.

It states that if a class meets the following criteria:

The class then receives a free __iter__ mixin method.

Therefore at least on this point of the documentation, mixin does not not require multiple inheritance, and is coherent with Definition 1.

Of course, the documentation may be conflicting at times, and other significant Python libraries may use the opposite term in their documentation.

The phrase Set mixin is also used on this page, implying that classes like Set and Iterator are Mixin classes.

In other languages

Answered by Ciro Santilli ๆ–ฐ็–†ๅ†ๆ•™่‚ฒ่ฅๅ…ญๅ››ไบ‹ไปถๆณ•่ฝฎๅŠŸ้ƒๆตทไธœ

Solution #4

Because a mixin is merely another python class that (could) obey the standards concerning classes called mixins, I conceive of them as a disciplined approach of employing multiple inheritance.

According to my understanding of the conventions that govern something called a Mixin, a Mixin:

That way, multiple inheritance’s potential complexity is limited, and it’s relatively straightforward to trace the flow of your program by restricting where you have to look (compared to full multiple inheritance). They’re a lot like Ruby modules.

When I wish to add instance variables (with greater flexibility than single inheritance allows), I usually use composition.

Having said that, I’ve seen instances variables in classes like XYZMixin.

Answered by Hamish Downer

Solution #5

A mixin is a type of multiple inheritance that is restricted. In some languages, the technique for adding a mixin to a class differs differently from inheritance in terms of syntax.

In the context of Python especially, a mixin is a parent class that provides functionality to subclasses but is not intended to be instantiated itself.

What might cause you to say, “that’s just multiple inheritance, not really a mixin” is if the class that might be confused for a mixin can actually be instantiated and used – so indeed it is a semantic, and very real, difference.

This is an OrderedCounter, according to the documentation:

It inherits from the collections module’s Counter and OrderedDict subclasses.

Counter and OrderedDict are designed to be instantiated and used independently. However, by subclassing both of them, we can create an ordered counter that reuses the code from each object.

This is an effective method for reusing code, but it can also be problematic. If it turns out there’s a bug in one of the objects, fixing it without care could create a bug in the subclass.

Mixins are sometimes marketed as a means to reuse code without the potential coupling difficulties that cooperative multiple inheritance, such as the OrderedCounter, can cause. You employ functionality that isn’t as tightly tied to the data when you use mixins.

A mixin, unlike the example above, is not meant to be used on its own. It adds new or different features to the system.

The socketserver library, for example, has a few of mixins from the standard library.

To allow for concurrency, the mixin methods override the methods defined in the UDPServer object description.

Process request appears to be the overridden method, and it also gives another method, process request thread. Here’s what the source code says:

Most objects will evolve beyond the utility of this repr: This is a mixin that is largely for demonstration purposes:

class SimpleInitReprMixin(object):
    """mixin, don't instantiate - useful for classes instantiable
    by keyword arguments to their __init__ method.
    """
    __slots__ = () # allow subclasses to use __slots__ to prevent __dict__
    def __repr__(self):
        kwarg_strings = []
        d = getattr(self, '__dict__', None)
        if d is not None:
            for k, v in d.items():
                kwarg_strings.append('{k}={v}'.format(k=k, v=repr(v)))
        slots = getattr(self, '__slots__', None)
        if slots is not None:
            for k in slots:
                v = getattr(self, k, None)
                kwarg_strings.append('{k}={v}'.format(k=k, v=repr(v)))
        return '{name}({kwargs})'.format(
          name=type(self).__name__,
          kwargs=', '.join(kwarg_strings)
          )

and its application would be:

class Foo(SimpleInitReprMixin): # add other mixins and/or extend another class here
    __slots__ = 'foo',
    def __init__(self, foo=None):
        self.foo = foo
        super(Foo, self).__init__()

And usage:

>>> f1 = Foo('bar')
>>> f2 = Foo()
>>> f1
Foo(foo='bar')
>>> f2
Foo(foo=None)

Answered by Aaron Hall

Post is based on https://stackoverflow.com/questions/533631/what-is-a-mixin-and-why-are-they-useful