6019
Comment:
|
46
Simply provide a link to the PEP
|
Deletions are marked like this. | Additions are marked like this. |
Line 1: | Line 1: |
Support for decorators was proposed for Python in [http://www.python.org/peps/pep-0318.html PEP 318], and will be implemented in Python 2.4. == What is a decorator == A decorator is a software design pattern. Decorators dynamically alter the functionality of a function, method, or class without having to directly use subclasses or change the source code of the function being decorated. For more information about the decorator pattern in general, see: * http://wiki.cs.uiuc.edu/patternStories/DecoratorPattern * http://en.wikipedia.org/wiki/Decorator_pattern == Debate about decorators in Python == The winning syntax as of now uses the '@' symbol, as described in [http://mail.python.org/pipermail/python-dev/2004-June/045516.html this message]. Mark Russell implemented this version. [http://mail.python.org/pipermail/patches/2004-July/015452.html Here] is the message describing the patch he checked in. There has been a long discussion about the syntax to use for decorators in Python. See for example these threads: * http://article.gmane.org/gmane.comp.python.devel/61569 * http://www.livejournal.com/users/jcalderone/3913.html == Examples == {{{ #!python @classmethod def foo (arg1, arg2): .... }}} == Related Resources == See also: MixIns, MetaClasses == Current Decorator Proposals == After the @decorator syntax was "accepted", lots of people threw up alarms and a huge series of threads started exploding on Python-dev. Here are the current alternatives that I could find that are being argued, with pros and cons: I give two examples that might be common uses in the future. Classmethod declarations, and something like static typing (adapters), declaring what type parameters a function expects and returns. '''A. pie decorator syntax''' {{{ @classmethod def foo(arg1,arg2): ... @accepts(int,int) @returns(float) def bar(low,high): ... }}} * + Java-like, so not completely unknown to everyone. * + Makes the syntax obvious visually * + Will not be silently ignored * + Compile-time * + Seperate from the def syntax (desired by some for making decoration stand out and keeping def the same) * - Seperate from the def syntax (undesired by some for simple decorators like classmethod/staticmethod) * - Ugly? * - The @ special character is used in IPython (...) * - Punctuation-based syntax raises Perlfears. * - Does not nessecarily '''B. list-before-def syntax''' {{{ [classmethod] def foo(arg1,arg2): ... [accepts(int,int), returns(float)] def bar(low,high): ... }}} * + C# like * + Can be made backwards compatible-ish, with a "hack" * + Doesn't cause breakage in existing code-searching tools * - Doesn't cause breakage in existing code-searching tools ----- /!\ Edit conflict! Other version: ----- * - Would not work an interactive mode (list would be interpreted right away) ----- /!\ Edit conflict! Your version: ----- ----- /!\ End of edit conflict ----- * - EuroPython didn't like it ( why? ) * - The backwards compatability wouldn't be portable to Jython * - Looks like a normal expression, but has "magic" behavior of altering a function object '''C. list-after-def syntax''' {{{ def foo(arg1,arg2) [classmethod]: ... def bar(low,high) [accepts(int,int), returns(float)]: ... }}} * + Also somewhat C#-like * + Was a "community favorite" at one time * + Clearly a part of function declaration * + Looks ok for simple decorators such as classmethod * + Won't break simplistic code analyzers or grep for function def * - Long lists of decorators/arguments cause ugly line wraps * - Guido didn't like (maybe because of line wrap issue?) '''D. list at top of function body syntax''' {{{ def foo(arg1,arg2): [classmethod] ... def bar(low,high): [accepts(int,int), returns(float)] ... }}} * + Also somewhat C#-like * + Consistent with how docstrings are used. * + Looks ok for simple or complex decorators * + Won't break simplistic code analyzers or grep for function def * + Solves line wrap problem with above proposal * 0 There is a hack that implements this now [http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/286147 here]. * - Guido's europython presentation said this didn't win out, but not why * 0 Perhaps decorators should be allowed before or after the docstring. If you have to choose, I'd choose making it before the docstring. ----- /!\ Edit conflict! Other version: ----- * - Adds 'magic' behavior to a normal python expression. ----- /!\ Edit conflict! Your version: ----- ----- /!\ End of edit conflict ----- '''E. pie decorator at top of function body syntax''' {{{ def foo(arg1,arg2): @classmethod ... def bar(low,high): @accepts(int,int) @returns(float) ... }}} * Same as above but with pie syntax. * Could use @doc to as a docstring alternative '''F. inline syntax''' {{{ def classmethod foo(arg1,arg2): ... ? }}} * + Simple * + Obviousely attached to the function * - Does not allow for arguments to the decorator inline, or multiple decorators * - The natural place where everyone looks for the function name now is a possible container for other information * - Complicates things like colorization and other functions of helper tools '''G. as decorator''' {{{ as classmethod def foo(arg1,arg2): ... ? }}} * + Non-punctuation based * + Does not use an existing mechanism with 'magic' behavior * - Guido specifically vetos: "as" means "rename" in too many logical, common places that are in-use, and decorators do not rename. '''H. with decorator, possibly indented?''' {{{ with classmethod: def foo(arg1,arg2): ... ? }}} * + The benefits of "as" without the renaming oddity. * + Reads as, "with decorator define function", which seems accurate. Such as, "with staticmethod define foobaction=savepage |
See http://www.python.org/peps/pep-0318.html |