On Thu, 20 Aug 2009 01:36:14 -0700, Paul Rubin wrote: > Steven D'Aprano <ste...@remove.this.cybersource.com.au> writes: >> As near as I can tell, a functor is just an object which is callable >> like a function without actually being implemented as a function, e.g.: > > No it's not anything like that either, at least as I'm used to the term > in programming or in mathematics. Maybe it's used other ways though.
According to Wikipedia, functor can be used as a synonym for "function object": http://en.wikipedia.org/wiki/Function_object which is what I was thinking of. So it seems there are at least two meanings for the word, neither of which seems to apply to this thread :) > As I'm used to it, it's a feature of certain static type systems. The > notion isn't that useful in Python I find the Haskell page entirely opaque and unintelligible. Well, perhaps not *entirely* opaque, but pretty close: it assumes a mathematical sophistication that I don't think I even had when I was getting my maths degree, let alone can remember two decades later. (Pity the poor VB coders wondering what Haskell is good for...) The Wikipedia page is a little better, but it's section on Examples is laughable -- the examples are as unintelligible to this reader as the description before them. But let me try an example to see if I've got it right: class Int2StrFunctor: def map1(self, n): if type(n) is not int: raise TypeError('argument must be an int') return "-"*n def map2(self, f): if type(f) is not type(lambda: None): raise TypeError('argument must be a function') # assume f takes an int, and returns another int def inner(n): return self.map1(f(n)) return inner The functor can take an int and return a string: >>> F = Int2StrFunctor() # F is a functor >>> F.map1(3) '---' It can also take a function (of int -> int) and return a new function (int -> str): >>> def myfunc(n): ... return n+2 ... >>> f = F.map2(myfunc) >>> f(3) '-----' >>> f(4) '------' There's nothing special about the methods map1() and map2(), I could call them anything I like, or even do this: >>> def __call__(self, arg): ... if type(arg) is int: ... return self.map1(arg) ... else: ... return self.map2(arg) ... >>> Int2StrFunctor.__call__ = __call__ >>> >>> F(2) '--' >>> F(myfunc)(0) '--' There are some technical restrictions on functors, relating to the sorts of functions and types (strictly "categories") they can accept, presumably to make them mathematically well-behaved. Have I got it correct? -- Steven -- http://mail.python.org/mailman/listinfo/python-list