’Almost real’ functor objects in C#
In these days of delegates, anonymous methods and lambda expressions, I’ve found it necessary to talk about good old functor objects. A functor is an object, that in some fashion you can treat as a function. Put another way, a functor is an object that you can call.
”But that is what delegates are!?”, you may say. Well, partially. Delegates are wrappers used to wrap functions; either member functions or static ones. Then when you call this delegate, the call is forwarded to the underlying function (typically named a callback function). Heres an example:
// Declare the delegate
public delegate void MyDelegate();// Define callback function
public void MyCallbackFunction()
{
Console.WriteLine("Callback function called!");
}
// Define a method that accepts a delegate
public void AcceptsCallbackFunction(MyDelegate func)
{
// call callback function
func();
}
// Pass function as argument
AcceptsCallbackFunction(MyCallbackFunction);
As mentioned, functors are not functions, but objects that behave like functions. A scenario where you could benefit from a functor is during list manipulations, when you need to maintain some kind of state:
// A class that will maintain some state, and provides a predicate that returns
// true at odd locations.
public class IsOddPosition
{
private int i = 0;public bool Predicate(int obj)
{
return (i++) % 2 != 0;
}
}
// Remove items add odd locations
List<int> list = new List<int> (new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9});
list.RemoveAll(new IsOddPosition().Predicate);
Here the IsOddPosition instance keeps track of how often the Predicate function is called, and behaves accordingly. Ccompared to a simple predicate function (one that for instance removes all numbers higher than 5), this predicate holds state information as RemoveAll is iterating through the list.
Ok, we’re almost there. The example uses a shorthand syntax introduced in C# 2.0 called delegate inference. Prior to 2.0 you would have to exlipcit instantiate the predicate like this:
list.RemoveAll(new Predicate<int> (new IsOddPosition().Predicate));
But, starting with 2.0, the explicit delegate stuff is implicitly done by the compiler, and all you have to write is:
list.RemoveAll(new IsOddPosition().Predicate);
Again, we’re almost there. What I would like to do is to further simplyfy this by allowing to use the IsOddPosition itself as the predicate, and not its member function. This is inspired and commonly used by C++, and the result should look like this:
list.RemoveAll(new IsOddPosition());
My first attempt was to derive the IsOddPosition class from the Predicate<int> class, but the attempt failed due to sealed keyword on the Predicate
public class IsOddPosition
{
private int i = 0;
public bool Predicate(int obj)
{
return (i++) % 2 != 0;
}
// Allow this class to implicitly cast to Predicate<int>
public static implicit operator Predicate<int>(IsOddPosition p)
{
return p.Predicate;
}
}
// Then use it like a C++ style functor object.
List list = new List<int>(new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9});
list.RemoveAll(new IsOddPosition());
Nice? I think so
- petter













September 13th, 2009 at 3:30 pm
Nice yes but not quite there yet. I would like to see something like in C++ where you can create your Functor object and than simply call it as a function, I couldn\\\’t make this happen:
public class Functor
{
public int FunctionToCallImplicitly(int a) { return a; }
}
public static class Program
{
public static void Main()
{
Functor f = new Functor();
int a = f(1);
}
}
Thanks for the writeup though.