Steven D'Aprano wrote: > Brett Cannon wrote: > >> PEP: 362 >> Title: Function Signature Object >> Version: $Revision$ >> Last-Modified: $Date$ >> Author: Brett Cannon <brett at python.org>, Jiwon Seo <seojiwon at gmail.com>, >> Yury Selivanov <yselivanov at sprymix.com>, Larry Hastings < >> larry at hastings.org> >> Status: Draft >> Type: Standards Track >> Content-Type: text/x-rst >> Created: 21-Aug-2006 >> Python-Version: 3.3 >> Post-History: 04-Jun-2012 >> >> >> Abstract >> ======== >> >> Python has always supported powerful introspection capabilities, >> including introspecting functions and methods. (For the rest of >> this PEP, "function" refers to both functions and methods). By >> examining a function object you can fully reconstruct the function's >> signature. Unfortunately this information is stored in an inconvenient >> manner, and is spread across a half-dozen deeply nested attributes. >> >> This PEP proposes a new representation for function signatures. >> The new representation contains all necessary information about a >> function >> and its parameters, and makes introspection easy and straightforward. > > It's already easy and straightforward, thanks to the existing > inspect.getfullargspec function. If this existing inspect function is > lacking something, the PEP should explain what, and why the inspect > function can't be fixed. > > >> However, this object does not replace the existing function >> metadata, which is used by Python itself to execute those >> functions. The new metadata object is intended solely to make >> function introspection easier for Python programmers. > > What happens when the existing function metadata and the __signature__ > object disagree? > > Are there use-cases where we want them to disagree, or is disagreement > always a sign that something is broken? > > > >> Signature Object >> ================ >> >> A Signature object represents the overall signature of a function. >> It stores a `Parameter object`_ for each parameter accepted by the >> function, as well as information specific to the function itself. > > There's a considerable amount of data recorded, including a number of > mappings (dicts?). This potentially increase the size of functions, and > the overhead of creating them. Since most functions are never > introspected, or only rarely introspected, it seems rather wasteful to > record all this data "just in case", particularly since it's already > recorded once in the function metadata and/or code object. > I agree with Stephen. Don't forget that each list comprehension evaluation involves creating a temporary function object. > > >> A Signature object has the following public attributes and methods: >> >> * name : str >> Name of the function. > > Functions already record their name (twice!), and it is simple enough to > query func.__name__. What reason is there for recording it a third time, > in the Signature object? > > Besides, I don't consider the name of the function part of the > function's signature. Functions can have multiple names, or no name at > all, and the calling signature remains the same. > > Even if we limit the discussion to distinct functions (rather than a > single function with multiple names), I consider spam(x, y, z) ham(x, y, > z) and eggs(x, y, z) to have the same signature. Otherwise, it makes it > difficult to talk about one function having the same signature as > another function, unless they also have the same name. Which would be > unfortunate. > > >> * qualname : str >> Fully qualified name of the function. > > What's the fully qualified name of the function, and why is it needed? > > > > [...] >> The structure of the Parameter object is: > >> * is_args : bool >> True if the parameter accepts variable number of arguments >> (``\*args``-like), else False. > > > "args" is just a common name for the parameter, not for the kind of > parameter. *args (or *data, *whatever) is a varargs parameter, and so > the attribute should be called "is_varargs". > > >> * is_kwargs : bool >> True if the parameter accepts variable number of keyword >> arguments (``\*\*kwargs``-like), else False. > > Likewise for **kwargs (or **kw, etc.) I'm not sure if there is a common > convention for keyword varargs, so I see two options: > > is_varkwargs > is_kwvarargs > > >> * is_implemented : bool >> True if the parameter is implemented for use. Some platforms >> implement functions but can't support specific parameters >> (e.g. "mode" for os.mkdir). Passing in an unimplemented >> parameter may result in the parameter being ignored, >> or in NotImplementedError being raised. It is intended that >> all conditions where ``is_implemented`` may be False be >> thoroughly documented. > > What to do about parameters which are partly implemented? E.g. > mode='spam' is implemented but mode='ham' is not. > > Is there a use-case for is_implemented? > > [...] >> Annotation Checker > >> def check_type(sig, arg_name, arg_type, arg_value): >> # Internal function that incapsulates arguments type checking > > /s/incapsulates/encapsulates > > > >> Open Issues >> =========== > > inspect.getfullargspec is currently unable to introspect builtin > functions and methods. Should builtins gain a __signature__ so they can > be introspected? I'm +0 on this, but care is needed as print and [].append are the same type in CPython. > > > >> When to construct the Signature object? >> --------------------------------------- >> >> The Signature object can either be created in an eager or lazy >> fashion. In the eager situation, the object can be created during >> creation of the function object. In the lazy situation, one would >> pass a function object to a function and that would generate the >> Signature object and store it to ``__signature__`` if >> needed, and then return the value of ``__signature__``. >> >> In the current implementation, signatures are created only on demand >> ("lazy"). > > +1 +1 also. See comment above about list comprehensions > > > >> Deprecate ``inspect.getfullargspec()`` and ``inspect.getcallargs()``? >> --------------------------------------------------------------------- > > > -1 > >> Since the Signature object replicates the use of ``getfullargspec()`` >> and ``getcallargs()`` from the ``inspect`` module it might make sense >> to begin deprecating them in 3.3. > > I think it is way to soon to deprecate anything. I don't think we should > even consider PendingDeprecation until at least 3.4. > > Actually, I would go further: leave getfullargspec to extract the > *actual* argument spec from the code object, and __signature__ to be the > claimed argument spec. Earlier, you state: > > "Changes to the Signature object, or to any of its data members, > do not affect the function itself." > > which leaves the possibility that __signature__ may no longer match the > actual argument spec, for some reason. If you remove getfullargspec, > people will have to reinvent it to deal with such cases. > > > >
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4