From c0b1eb3d65caba6848cc2df55ce658f2cb2c246d Mon Sep 17 00:00:00 2001 From: Raymond Hettinger Date: Sun, 22 Apr 2012 21:32:34 -0700 Subject: [PATCH] Restore the prohibition against using function annotations in the standard library. At Guido's request, added notes regarding issues observed with various developer's early attempts to use function annotations. --- pep-0008.txt | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 52 insertions(+), 1 deletion(-) diff --git a/pep-0008.txt b/pep-0008.txt index 52606490b..a01d0e237 100644 --- a/pep-0008.txt +++ b/pep-0008.txt @@ -140,7 +140,7 @@ appropriately. The preferred place to break around a binary operator is *after* the operator, not before it. Some examples:: class Rectangle(Blob): - + def __init__(self, width, height, color='black', emphasis=None, highlight=0): if (width == 0 and height == 0 and @@ -887,6 +887,57 @@ Programming Recommendations No: if greeting == True: Worse: if greeting is True: +- The Python standard library will not use function annotations as + that would result in a premature commitment to a particular + annotation style. Instead, the annotations are left for users to + discover and experiment with useful annotation styles. + + Early core developer attempts to use function annotations revealed + inconsistent, ad-hoc annotation styles. For example: + + * ``[str]`` was ambiguous as to whether it represented a list of + strings or a value that could be either *str* or *None*. + + * The notation ``open(file:(str,bytes))`` was used for a value that + could be either *bytes* or *str* rather than a 2-tuple containing + a *str* value followed by a *bytes* value. + + * The annotation ``seek(whence:int)`` exhibited an mix of + over-specification and under-specification: *int* is too + restrictive (anything with ``__index__`` would be allowed) and it + is not restrictive enough (only the values 0, 1, and 2 are + allowed). Likewise, the annotation ``write(b: bytes)`` was also + too restrictive (anything supporting the buffer protocol would be + allowed). + + * Annotations such as ``read1(n: int=None)`` were self-contradictory + since *None* is not an *int*. Annotations such as + ``source_path(self, fullname:str) -> object`` were confusing about + what the return type should be. + + * In addition to the above, annotations were inconsistent in the use + of concrete types versus abstract types: *int* versus *Integral* + and set/frozenset versus MutableSet/Set. + + * Some annotations in the abstract base classes were incorrect + specifications. For example, set-to-set operations require + *other* to be another instance of *Set* rather than just an + *Iterable*. + + * A further issue was that annotations become part of the + specification but weren't being tested. + + * In most cases, the docstrings already included the type + specifications and did so with greater clarity than the function + annotations. In the remaining cases, the docstrings were improved + once the annotations were removed. + + * The observed function annotations were too ad-hoc and inconsistent + to work with a coherent system of automatic type checking or + argument validation. Leaving these annotations in the code would + have made it more difficult to make changes later so that + automated utilities could be supported. + References ==========