> After the code has stabilized I can probably go back to write type hints [...] but I'm not sure that this would provide very much value. I think most developers who revisit their projects 6+ months later would disagree with the second part of this statement. My typical flow for "quick scripts" is: on first pass I'll add basic type hints (typing ":str" after a func param takes .2 seconds) for more complex data struc…
Python type hints may not be not for me in practice
171–180 of 209 posts
Re: Python type hints may not be not for me in practice
#172Earlier quoted context omitted.
I have the opposite experience: Inserting a library that wraps an existing one to add new features has been a nightmare in every statically typed language I’ve used — including times it’s virtually impossible because you’d need the underlying library to understand the wrapper type in its methods. In Python (with duck typing), that’s a complete non-issue.
Can you give an example? I think part of the problem is that mixins and such are so hard to do in most statically typed languages that programmers just don’t code things that way. I see your point - I certainly find myself reaching for clever high level patterns less in typescript than I do in JavaScript because complex typing can get in the way. But also, programs that make heavy use of metaprogramming are often, al…
I used a HTTP requests library in a nuxtjs app (probably nuxt's native library) and I spent too much of my time conjuring the request and response types that would please the type checker. It was extremely frustrating because the code would work in Javascript but the compiler wouldn't accept it because of typing.
I can't give you the details because I'm not at my computer now but the type was a mix of HTTP verbs and the structure of the JSON response. I gave up after a while and rewrote the code using fetch and no types. If they stand between me and the final result they can go down the drain.
Re: Python type hints may not be not for me in practice
#173Earlier quoted context omitted.
> when types weren't an option we weren't going towards the cliff Erm yes we were. Untyped Python wasn't magically tolerable just because type hints hadn't been implemented yet.
How come all those unicorns were built with intolerable Python/Ruby, not Java/C#/Go? https://charliereese.ca/y-combinator-top-50-software-startup...
Besides nobody is claiming that it's impossible to build a successful products with dynamic typing. It's just not as good. You can build a successful product with zero comments in your codebase, doesn't mean it's a good idea.
Re: Python type hints may not be not for me in practice
#174Earlier quoted context omitted.
Can you give an example? I think part of the problem is that mixins and such are so hard to do in most statically typed languages that programmers just don’t code things that way. I see your point - I certainly find myself reaching for clever high level patterns less in typescript than I do in JavaScript because complex typing can get in the way. But also, programs that make heavy use of metaprogramming are often, al…
I'm not the person you asked the question to but I had an unpleasant experience with Typescript recently. I used a HTTP requests library in a nuxtjs app (probably nuxt's native library) and I spent too much of my time conjuring the request and response types that would please the type checker. It was extremely frustrating because the code would work in Javascript but the compiler wouldn't accept it because of typing.…
It doesn't happen too often, but its definitely annoying.
In cases like this, the easiest way is to just add as any to your expression - which essentially turns off type checking for that expression. Maybe that's what you did?
fetch('foo.json', {...} as any)
I don't think there's anything wrong with this. Using typescript types for only 95% of your code rather than 100% still provides a lot of value in my opinion.You can also ctrl+click on functions like this and read the actual types they're expecting.
Re: Python type hints may not be not for me in practice
#175Earlier quoted context omitted.
If it’s 100x better than no types, then probably 10x better than C++ type system. It takes some time to unlearn using dicts everywhere, but then namedtuples become your best friend and noticeably improve maintainability. Probably the only place where python type system feels inadequate is describing json-like data near the point of its (de)serialization.
Pretty much anywhere you're tempted to use a namedtuple, you should be using a dataclass[0] instead. And typing JSON-like data is possible with TypedDict[1]. [0] https://docs.python.org/3/library/dataclasses.html [1] https://docs.python.org/3/library/typing.html#typing.TypedDi...
To me, namedtuples are a convenience to give a nicer syntax than ordinary tuples in scenarios where I don't want the overhead of having to store a copy of all the keys with every object, like a dict would. Dataclass seems to be even more stuff on top of a class which is effectively even more stuff on top of a dict, but all the use cases of namedtuples are those where you want much less stuff than an ordinary class has. And I don't want to have to define a custom class just as I often don't define a custom namedtuple in my code but use the one the database driver generates based on the query, which is a very common use case for namedtuples as efficient temporary storage of data that then gets processed to something else.
Re: Python type hints may not be not for me in practice
#176Earlier quoted context omitted.
The old stuff never stopped working, though. You can still use Optional, Union, TypeAlias, and import collection protocols from typing. You don't have to migrate if you don't want to. They're not even deprecated.
I encourage you to open the `typing` documentation [0] and search for the word `deprecated`. Spoiler alert: the search result will be three-figure. Some of the results are already scheduled for removal. [0]: https://docs.python.org/3/library/typing.html
> The redundant types are deprecated as of Python 3.9. However, while the aliases may be removed at some point, removal of these aliases is not currently planned. As such, no deprecation warnings are currently issued by the interpreter for these aliases.
The idea is that new code shouldn't use them, but they work perfectly fine and will keep working in the near future. Even if they decide to remove these at some point, you're looking at several years before it actually happens, and you'll have plenty of time to migrate.
As it stands, you can use them to your heart's content without issues.
Re: Python type hints may not be not for me in practice
#177Earlier quoted context omitted.
The old stuff never stopped working, though. You can still use Optional, Union, TypeAlias, and import collection protocols from typing. You don't have to migrate if you don't want to. They're not even deprecated.
I've seen multiple major projects (such a sphinx) break on newer versions of Python due to changes in typing. Typing should make the code more robust, not less.
Re: Python type hints may not be not for me in practice
#178Earlier quoted context omitted.
I'm not the person you asked the question to but I had an unpleasant experience with Typescript recently. I used a HTTP requests library in a nuxtjs app (probably nuxt's native library) and I spent too much of my time conjuring the request and response types that would please the type checker. It was extremely frustrating because the code would work in Javascript but the compiler wouldn't accept it because of typing.…
Sounds like a bug in the type definitions. Thats an unfortunate consequence of typescript being glued to javascript: If you import a package that is authored in javascript, there's no guarantee that the type definitions are written correctly or kept up to date. Sometimes they don't exist at all. It doesn't happen too often, but its definitely annoying. In cases like this, the easiest way is to just add as any to your…
const response = await fetch(
url,
{
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(reqData),
}
);
const resData: ApiResponse = await response.json();
then I parsed resData. The JSON in the response is still type checked but I don't have to fight anymore with the HTTP library. I can't remember what it was as it never made it into a commit.Re: Python type hints may not be not for me in practice
#179Earlier quoted context omitted.
Sounds like a bug in the type definitions. Thats an unfortunate consequence of typescript being glued to javascript: If you import a package that is authored in javascript, there's no guarantee that the type definitions are written correctly or kept up to date. Sometimes they don't exist at all. It doesn't happen too often, but its definitely annoying. In cases like this, the easiest way is to just add as any to your…
I did this: const response = await fetch( url, { method: 'POST', headers: { 'Content-Type': 'application/json', }, body: JSON.stringify(reqData), } ); const resData: ApiResponse = await response.json(); then I parsed resData. The JSON in the response is still type checked but I don't have to fight anymore with the HTTP library. I can't remember what it was as it never made it into a commit.
Re: Python type hints may not be not for me in practice
#180Earlier quoted context omitted.
No it hasn’t? C++ type system has hardly changed (until concepts) and is one of the most powerful available. A certain generation of devs thought types were academic nonsense and then relearned the existence of those features in other languages. Now they are zealots about using them.
I think the point is that in newer languages like typescript, the price paid for static typing is lower because type inference does so much of the leg work. You get all the benefits of static typing, and the cost is usually tiny - you just need to define your types (a valuable exercise regardless) and add them to function signatures. We’ve come a long way from the C++ or Java I wrote when I was young, where types wer…
#include
auto func(auto x, auto y) -> auto {
return x + y;
}
auto main() -> int {
auto i = func(1, 2);
auto s = func(std::string("a"), std::string("b"));
}
`int` is required as a return type from `main`, but everything else is inferred. This works because `func` becomes a template function where each parameter type is a separate template type, so you get compile-time duck typing. It also works with concepts (e.g. `std::integral auto x`).It's quite neat, but I don't think anyone actually writes code this way, except for lambdas.