On Thu, Apr 30, 2015 at 01:41:53PM +0200, Dima Tisnek wrote: > # Syntactic sugar > "Beautiful is better than ugly, " thus nice syntax is needed. > Current syntax is very mechanical. > Syntactic sugar is needed on top of current PEP.
I think the annotation syntax is beautiful. It reminds me of Pascal. > # internal vs external > @intify > def foo() -> int: > b = "42" > return b # check 1 > x = foo() // 2 # check 2 > > Does the return type apply to implementation (str) or decorated callable > (int)? I would expect that a static type checker would look at foo, and flag this as an error. The annotation says that foo returns an int, but it clearly returns a string. That's an obvious error. Here is how I would write that: # Perhaps typing should have a Function type? def intify(func: Callable[[], str]) -> Callable[[], int]: @functools.wraps(func) def inner() -> int: return int(func()) return inner @intify def foo() -> str: b = "42" return b That should, I hope, pass the type check, and without lying about the signature of *undecorated* foo. The one problem with this is that naive readers will assume that *decorated* foo also has a return type of str, and be confused. That's a problem. One solution might be, "don't write decorators that change the return type", but that seems horribly restrictive. Another solution might be to write a comment: @intify # changes return type to int def foo() -> str: ... but that's duplicating information already in the intify decorator, and it relies on the programmer writing a comment, which people don't do unless they really need to. I think that the only solution is education: given a decorator, you cannot assume that the annotations still apply unless you know what the decorator does. > How can same annotation or a pair of annotations be used to: > * validate return statement type > * validate subsequent use > * look reasonable in the source code > > > # lambda > Not mentioned in the PEP, omitted for convenience or is there a rationale? > f = lambda x: None if x is None else str(x ** 2) > Current syntax seems to preclude annotation of `x` due to colon. > Current syntax sort of allows lamba return type annotation, but it's > easy to confuse with `f`. I don't believe that you can annotate lambda functions with current syntax. For many purposes, I do not think that is important: a good type checker will often be able to infer the return type of the lambda, and from that infer what argument types are permitted: lambda arg: arg + 1 Obviously arg must be a Number, since it has to support addition with ints. > # local variables > Not mentioned in the PEP > Non-trivial code could really use these. Normally local variables will have their type inferred from the operations done to them: s = arg[1:] # s has the same type as arg When that is not satisfactory, you can annotate variables with a comment: s = arg[1:] #type: List[int] https://www.python.org/dev/peps/pep-0484/#id24 > # global variables > Not mentioned in the PEP > Module-level globals are part of API, annotation is welcome. > What is the syntax? As above. > # comprehensions > [3 * x.data for x in foo if "bar" in x.type] > Arguable, perhaps annotation is only needed on `foo` here, but then > how complex comprehensions, e.g. below, the intermediate comprehension > could use an annotation > [xx for y in [...] if ...] A list comprehension is obviously of type List. If you need to give a more specific hint: result = [expr for x in things if cond(x)] #type: List[Whatever] See also the discussion of "cast" in the PEP. https://www.python.org/dev/peps/pep-0484/#id25 > # class attributes > s = socket.socket(...) > s.type, s.family, s.proto # int > s.fileno # callable > If annotations are only available for methods, it will lead to > Java-style explicit getters and setters. > Python language and data model prefers properties instead, thus > annotations are needed on attributes. class Thing: a = 42 # can be inferred b = [] # inferred as List[Any] c = [] #type: List[float] -- Steve _______________________________________________ Python-Dev mailing list Python-Dev@python.org https://mail.python.org/mailman/listinfo/python-dev Unsubscribe: https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com