Functors combine functions and attribute sets
A functor is a polymorphic data type that can represent both a
lambda function (x: x
) and an attribute set ({ key = value; }
).
This means that the Atribute set can hold data in the form of attributes.
And also be a lambda function that can operate on that data.
-> The lambda function can access the attributes of the attribute set often called self
.
In the following example, build
is both an attribute set and a lambda.
__functor
is a reserved attribute name that turns the attribute set build
into a functor.
{
build = {
foo = 1;
__functor = self: _arg: self.foo;
};
}
The attribute set build
can now be used as a lambda via function application
.
nix-repl> build "linux"
=> 1
But at the same time build
is still an Attribute set.
nix-repl> build
=> { __functor = «lambda»; foo = 1; }
Functors find practical applications including some in nixpkgs:
lib.makeOverridable
lib.setFunctionArgs
lib.mirrorFunctionArgs
lib.types
and lib.options
(Noogle opinion)
The use of functor should be avoided and is often unnecessary.
Using them can add up in complexity and makes is hard to learn and maintain a certain piece of code.