[Python-3000] Class Decorators + ctypes (Was: yes to class decorators)
Talin
talin at acm.org
Thu Nov 16 06:41:43 CET 2006
tomer filiba wrote:
> here are some usecases to class decorators:
What I would like is a way to use class decorators, combined with
ctypes, to effectively 'declare' a C structure using Python syntax.
Right now you can use ctypes to declare a C struct, but the syntax isn't
very Python-like:
class RECT(Structure):
_fields_ = [("upperleft", POINT),
("lowerright", POINT)]
Even with class decorators, however, there is still a missing piece -
there's no way to decorate a variable declaration. That's because
there's no equivalent of 'def' for variables. (Thinking about it, it
does seem like there's an asymmetry here - you can define functions
using 'def' or using assignment, but you can define variables only using
assignment.)
Here's a more specific proposal: The token '->' has been proposed (as
part of the argument decorator syntax) as a way to indicate the return
type of a function definition. What if a similar syntax could be used to
define and create a class variable?
Here's an example. I realize that the syntax may look strange, but it's
all a logical extension of things that have already been proposed and
for the most part accepted:
@cstruct
class CPoint:
def x -> float
def y -> float
Under the hood, here's what's happening:
1) 'def' without an argument list defines a variable instead of a function.
2) The '-> float' is merely advisory - it has no meaning except to the
decorator, just as has been proposed with argument decorators.
3) The @cstruct decorator changes the way that the class is evaluated,
adding an implicit decorator to each definition. In this case, it
evaluates the argument decorators and adds a field definition for each one.
One unresolved issue is what exactly gets assigned to 'x' and 'y' at the
time the class definition is evaluated. Ordinarily, 'def' adds a named
entry to the class dict. In a normal function declaration, the part
after the colon defines a suite, which is the value assigned to the name.
I first thought about allowing the same colon to be used to define the
value to assign to the variable, i.e.:
def x -> float: 0
However, this is inconsistent with the use of the colon in other places
in Python, which generally introduces a suite.
An alternative would be to use an assignment operator:
def x -> float = 0
The only difference between this and simply 'x = 0' is that the 'def'
statement, unlike an assignment, can be decorated.
A different approach would be to say that the class decorator can
overload the '__setattr__' method on the class itself during class creation:
@cstruct
class CPoint:
x = FLOAT
y = FLOAT
I think that you would *only* want to do this override during the
initial evaluation of the class. Once the class was fully created, I
would think that you'd want to be able to do "CPoint.x = value" without
triggering the decorator's override.
(As a bit of trivia that may be of interest: The latest proposals for
extending the C++ language allow a function return type to be declared
using the "(args) -> returntype" syntax. The primary reason for doing
this is to avoid certain syntactical ambiguities and to allow support
for lambda functions in C++, but there are some other advantages to
doing so when using functions as template arguments.)
-- Talin
More information about the Python-3000
mailing list