Generators should be treatable as lazy lists in the end, and lists should have a common interface whether they are lazy or eager. Someone should figure out a way to have us write code at a higher abstraction level and have same interface for lazy vs eager data structures.
...but it's not gonna happen in a dynamic language like Python. And I can't say I like the "solution" of having the entire language be lazy like Haskell either :|
We're stuck with "casting generators" for now, I guess, but it really does suck!
With that said...
> In theory a "sufficiently smart language" should have a feature to understand that `thing[3]` can be translated to "call `next()` 3 times
This might be a newbie trap, because next() isn't the same as indexing. What happens if I perform `thing[7]` followed by `thing[5]`? Should performing `thing[7]` put 1-6 in memory and turn the object into a generator-list hybrid?
You're right here. Probably can't work like that since generators are too general, you can't expect them to be rewindable or to not have side effects... prob you'd need a more specialized concept like a "lazy list" that would be a subtype of generator with some extra restrictions that would make it possible to implement the "hybrid" structure as an implementation detail without changing semantics.
Anyway... it would be too much work and probably would turn into a footgun.
They seem to exist only to do lots of stuff in one single line of code. You end up with totally impenetrable unreadable perl-esq garbage write-once-read-never code that is too clever for its own good. And people say python is easy to learn and good for beginners...!
A better approach would be something like Java Streams/.net Lync/RxX pattern IMO. Explicit, clear, no magic, logical.
g = [i for i in list if x == 3] -> g = []; for i in list: if x == 3: g.append(i);
How could that be improved? That's 3-4 LOC minimum in any other language
My main grip is python's ternary operators, since the True value is evaluated before the condition, if you are doing ternaries on things that might throw exceptions the False value has to come first
value = 0 if key not in dic else dic[key] * 5
rather than (throws indexerror if key isn't in dic)
value = dic[key] * 5 if key in dic else 0
dic = {k: v for k, v in dic.items() if k in other_dic and v == "bar"}
> "How could that be improved? That's 3-4 LOC minimum in any other language"If I'm understanding the comprehension correctly,
(into {} (filter (fn [[k v]] (and (get other-dic k) (= v "bar"))) dic))
Though, for readability, I'd likely write it as: (->> dic
(filter (fn [[k v]]
(and (get other-dic k)
(= v "bar"))))
(into {}))
Legibility is in the eye of the beholder.(for) k, v in dic.items()
which is just
k, v = (<key>, <value>) for every key value pair in the dictionary
I posted due to your claim regarding all other languages necessitating increased verbosity. I should have left it lie, as I didn't intend to promote a language war, just to post a counter example. My apologies.
dic = dic.where((k, v) => k in other_dic and v == "bar").todict()
dic.iter().filter(|k, v| other_dic.contains(k) && v == "bar").collect();
it's one line, though I'd format it as 3 for readability (list comprehension is hard to read and functional style composes better.
https://news.ycombinator.com/newsguidelines.html
For example, instead of putting someone's article down as sophomoric, you could explain what's different and possibly better about Haskell list comprehensions.
All these politeness comments are a speed bump that distracts from the real issues.
I used to think similarly about this to what you express, because I've always enjoyed reading about the sort of discourse in which devastating wit is exchanged. But eventually I realized that it doesn't translate into this context at all. This is a case of 'the medium is the message'. When you have millions of people who don't know each other all potentially interacting at the same time, the dynamics are so different as to be incommensurable with, say, small debates, literary journals, elite social events, and other places where the groups are small and highly cohesive. Here are some previous explanations about this:
https://hn.algolia.com/?dateRange=all&page=0&prefix=true&sor...
https://news.ycombinator.com/item?id=15378909
https://news.ycombinator.com/item?id=9378899
https://news.ycombinator.com/item?id=7906377
https://news.ycombinator.com/item?id=7742471
The bottom line is that having a forum like HN be open to everybody comes at the cost of some blandness.