[Python-Dev] Python Library Addition: First-class Procedure Signatures (original) (raw)
Isaac Morland ijmorlan at cs.uwaterloo.ca
Wed Nov 14 19:30:21 CET 2007
- Previous message: [Python-Dev] Suggestions for Improvements to namedtuple
- Next message: [Python-Dev] Python Library Addition: First-class Procedure Signatures
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
For another project (see my previous email on named tuples), I needed to represent procedure signatures, and use them to expand arguments into the dictionary of values that exists when execution of a procedure starts. To my surprise, this capability didn't seem to be provided by the Python library, even though it clearly is present within the Python system somewhere.
So I wrote a Signature class. Instances of the class represent all the information present between the parentheses of a procedure definition. Properties are provided to get the information out, and an expand_args method can be called to expand arguments into a dictionary. This expand_args method implements (if I've done it right) the argument conversion part of section 5.3.4 of the Python Reference Manual (http://docs.python.org/ref/calls.html).
I've put the code below, but I wonder if the real solution is just to create an interface to already-existing capability? It occurs to me that the implementation is likely to be in the interpreter itself and not written in Python.
One possible improvement (and I'm not sure it's better, so I'm just putting it out there): perhaps expand_args should be renamed to call. Then essentially a Signature object would be a procedure whose body is just "return locals ()".
class Signature (object): def init (self, argnames, excessargs=None, excesskeys=None, defaults=None): self.__argnames = tuple (argnames) self.__excessargs = excessargs self.__excesskeys = excesskeys if defaults is None: defaults = {} self.__defaults = dict (defaults)
@property
def argnames (self):
return self.__argnames
@property
def excessargs (self):
return self.__excessargs
@property
def excesskeys (self):
return self.__excesskeys
def defaults (self):
return dict (self.__defaults)
def expand_args (self, *args, **keys):
# Start with defaults
result = self.defaults ()
# Assign positional arguments
for i in range (min (len (args), len (self.argnames))):
result[self.argnames[i]] = args[i]
# Assign keyword arguments
for arg in self.argnames:
if arg in keys:
if arg in result:
raise TypeError
result[arg] = keys[arg]
del keys[arg]
# Check for missing arguments
for i in range (len (args), len (self.argnames)):
if not self.argnames[i] in result:
raise TypeError
# Excess positional arguments (*args parameter)
if self.excessargs is None:
if len (args) > len (self.argnames):
raise TypeError
else:
result[self.excessargs] = args[len (self.argnames):]
# Excess keyword arguments (**keys parameter)
if self.excesskeys is None:
if keys:
raise TypeError
else:
result[self.excesskeys] = keys
return result
Isaac Morland CSCF Web Guru DC 2554C, x36650 WWW Software Specialist
- Previous message: [Python-Dev] Suggestions for Improvements to namedtuple
- Next message: [Python-Dev] Python Library Addition: First-class Procedure Signatures
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]