Nick Coghlan <[EMAIL PROTECTED]> wrote: > Raymond Hettinger wrote: > >* The instance method limitation never came up for me. However, it > >bites to have a tool working in a way that doesn't match your mental > >model. We have to document the limitations, keep them in mind while > >programming, and hope to remember them as possible causes if bugs ever > >arise. It would be great if these limitations could get ironed out. > > The 'best' idea I've come up with so far is to make partial a class factory > instead of a straight class, taking an argument that states how many > positional arguments to prepend at call time. A negative value would result > in the addition of (len(callargs)+1) to the position at call time.
Other dynamic languages, like Lisp, are in the same boat in this respect--real currying (and things that look like it) doesn't work too well because the API wasn't designed with it in mind (curried languages have functions that take less-frequently-changing parameters first, but most other languages take them last). Scheme has a nice solution for this in SRFI 26 (http://srfi.schemers.org/srfi-26/). It looks like this: (cut vector-set! x <> 0) That produces a function that takes one argument. The <> is an argument slot; for every <> in the cut form, the resultant callable takes another argument. (This explanation is incomplete, and there are some other features; read the SRFI for details.) I've been using something similar in Python for a while, and I really like it. It doesn't look as good because the slot has to be a real object and not punctuation, but it works just as well. For example: cut(islice, cutslot, 0, 2) That's pretty readable to me. My version also allows the resultant callable to take any number of parameters after the slots have been satisfied, so partial is just the special case of no explicit slots. Perhaps a full example will make it clearer: >>> def test(a, b, c): ... print 'a', a, 'b', b, 'c', c ... >>> f = cut(test, cutslot, 'bravo') >>> f('alpha', 'charlie') a alpha b bravo c charlie Here, b is specialized at cut time, a is passed through the slot, and c is passed through the implicit slots at the end. The only thing this can't do is a generic right-"curry"--where we don't know how many parameters come before the one we want to specialize. If someone wants to do that, they're probably better off using keyword arguments. So far, my most common use for this is to specialize the first argument to map, zip, or reduce. Very few cases actually need an explicit cutslot, but those that do (like the islice example above) look pretty good with it. My reasons for using cut instead of lambda are usually cosmetic--the cut form is shorter and reads better when what I'm doing would be a curry in a language designed for that. Throw in a compose function and I almost never need to use lambda in a decorator <ducks and runs from the anti-lambda crowd>. _______________________________________________ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com