3 ms·
Yes. I like to use type annotations on functions because it's documentation. If you use good names then it makes docstrings redundant. I'm thinking something li
by globular-toast 2y ago
Yes. I like to use type annotations on functions because it's documentation. If you use good names then it makes docstrings redundant. I'm thinking something like this:
def bounding_box(points: list[Point]) -> Box:
...
A decent IDE will be able to quickly jump to definition of those Box and Point etc. if you need it. This is much better than having a docstring and having to look stuff up manually. The fact you can run a static type checker like mypy is a bonus!
I also really like being able to document the imperative code like `def do_thing() -> None`. Of course, it's completely up to the programmer to follow the rule of not doing side effects in routines that return something.
But having to do it everywhere? Ugh. I don't think people realise how powerful duck typing is for doing polymorphic code. I can write something like:
def mean(things):
return sum(things)/len(things)
And I don't care what concrete type you pass me as long as it supports `sum` and `len`. What am I going to do, define an ABC or typing.Protocol called `ListLike` or something? Hell no, I've got better things to do.
But of course learning when to define static types vs when not to comes down to experience. Python treats you like an adult. I feel like a lot of people who want static typing everywhere want it as training wheels for other devs they don't trust to make the right judgement calls.
- maleldil 2y agoYou picked a poor example for `mean` because there's a very easy answer: collections.abc.Sequence – typing.Sequence in earlier versions – an object that supports __getitem__ and __len__. You can check the collections.abc documentation[1] for the available protocols; you might be surprised about how much they cover already. I often use Sequence/Iterable or Mapping as parameter types instead of concrete types like list or dict. > I feel like a lot of people who want static typing everywhere want it as training wheels for other devs they don't trust to make the right judgement calls. Now, I want it because it makes my life a lot easier. It finds many classes of errors before runtime and improves auto-completion in my editor. For most programs, it's not a lot of effort. The frustrating part is interfacing with untyped libraries while using strict type-checking, but thankfully, more and more libraries are adopting typing. The type system itself is fine: most things you want to express are doable, but it's not at the same level of complexity as Typescript. It's certainly a better type system than Go's for example. [1] https://docs.python.org/3/library/collections.abc.html https://docs.python.org/3/library/collections.abc.html
- globular-toast 2y agoHmph, I knew someone would point out that `Sequence` exists or whatever... The point was really that this could be a new type that isn't fully captured by something built in. As for `collections.abc.Sequence`, using an ABC sucks because then you have to define a class and inherit from it. I don't want to do that. I just want to pass something that conforms to the duck type. Are these now also defined as structural types/Protocols?
- gpderetta 2y ago> But having to do it everywhere? Ugh. I don't think people realise how powerful duck typing is for doing polymorphic code. Duck typing is indeed powerful, but it does not need to be a runtime check. > What am I going to do, define an ABC or typing.Protocol called `ListLike` or something? Yes, how am I going to know what types I can pass to mean instead? I would go to the extreme of saying that a lot of python code should be type annotated (if annotated at all) with protocols instead of concrete or base classes. Of course until type checking is properly integrated in the interpreter this is all kind of pointless.
- globular-toast 2y ago> Yes, how am I going to know what types I can pass to mean instead? Oh, if I'm writing it for you (ie. I'm writing a library) then I'll put documentation (probably as type annotations, as I said in the first half of my comment). But a lot of code I write is just for me, or is going to be part of a completely self-contained project and it would be obvious from context what to pass. Like I said, it's a judgement call that Python expects you to be able to make.
- binary132 2y agoif only there was some way for this structural documentation to also cause incorrect programs to be rejected