Complicated comprehensions are not clever or impressive, they’re annoying.
Complicated comprehensions are not clever or impressive, they’re annoying.
Haskell list comprehensions limited to two clauses, SQL queries limited to a single FROM and a WHERE, or a FROM and a JOIN sound pretty limited. I use Python comprehensions to do those same kinds of data querying without leaving the Python context, so seems weird to limit myself for the same reason.
Using imperative constructs certainly isn't wrong, but they tend to crawl off the right hand side of the page.
I suppose this is only true in combination with verbose function names that capture the logic of the operation you're performing, with the comprehension expressing how this logic is composed. In my mind, comprehensions are sugar over map(), filter(), etc., and before I was using comprehensions I had a mess of nested calls to these functions with lots of lambdas. Comprehensions are a big step up from that as far as readability goes.
americans := SELECT username FROM users WHERE country = "us";
SELECT url, visits FROM posts, americans ON posts.author = americans.username ORDER BY visits DESC LIMIT 10;With americans as (select ...) select from ..., americans ...
https://www.draxlr.com/blogs/common-table-expressions-and-it...
It could work as an expression which gets injected into the 2nd query. So the second query would effectively have a nested SELECT statement as defined by the americans expression.
But this has the downside that if you reuse americans you have to know that it will be recomputed at each query. So unless you know the semantics of these variable-expression things over time you get race conditions. The solution again would be to wrap everything in a transaction, but at that point you just have to constantly think about transactions, which you don’t if your query is a one-liner.
Also good luck writing a query planner that has to efficiently take into account variables.
But it was completely incomprehensible and unmaintainable. So got replaced by me later.
Instead of writing for loops he would write comprehensions everywhere because "list comprehensions are pythonic".
Think like:
[send_welcome_email(u) for u in users]
Just hanging out in the middle of the module or function.sent = [(u, send_welcome_email(u)) for u in users]
not_sent = users - {u for u in users if send_welcome_email(u)}
Just make sure it isn't consuming a lot of RAM and it's totally OK.
sum(
a + b
for a in range(10)
if a % 2 == 0
for b in range(10)
)