5 ms·
The generic slice functions would certainly reduce boiler plate, but what I miss in comparison to Rust is the concept of iterators. In Rust if you were to itera
by mutatio 5y ago
The generic slice functions would certainly reduce boiler plate, but what I miss in comparison to Rust is the concept of iterators. In Rust if you were to iterate over words in a string you'd get borrowed words, so in practice lots of things are non-allocating (unless you choose to collect / take ownership) - in Go etc. instead of windowing over a string you typically fully allocate the []string result (e.g. strings.Split / strings.Fields). Sub-slicing in Go can be used to make your own iterators, but the ergonomics take a hit.
- iib 5y agoYes, iterators are typically a hard[1] problem in Go. I think this essay[2] describes perhaps the closest lazy eval iterator pattern in Go, which is much more complex to write than languages like Python. [1] https://ewencp.org/blog/golang-iterators/index.html https://ewencp.org/blog/golang-iterators/index.html [2013] [2] www.catb.org/~esr/reposurgeon/GoNotes.html [2020]
- johnmaguire 5y agoClickable: http://www.catb.org/~esr/reposurgeon/GoNotes.html http://www.catb.org/~esr/reposurgeon/GoNotes.html
- throwaway894345 5y agoI don’t understand what’s hard about iterators in Go after reading that article. I’ve written a lot of Python and Go (15 and 10 years respectively) as well as a bit of Rust and while iterators are certainly simpler in Python and Rust since Go lacks generics, most of the “challenges” presented in the article seem petty (complaints about for loops). The easiest way to write an iterator in Go is the closure/generator method and you can use it in a for loop like so: for x := next(); x != nil; x = next() { ... } Not as nice as a for/range but not a real problem. With generics we can have libraries that operate on iterators like map, filter, reduce although I also think people make way too big a deal about a tiny bit of for loop boilerplate (there are legitimate reasons for generics but I don’t think small amounts of boilerplate are among them).
- psanford 5y agoThere's nothing hard about writing iterators in go.
- eloff 5y agoRust iterators are beautiful. If you've ever implemented C++ iterators, you'll be pleasantly surprised at how elegant it is in Rust by comparison (actually you could replace iterators with about any language feature and the above holds true.) I really like Rust as a language, it's like a lightsaber, an elegant weapon from a more civilized era. Go feels a bit more like a blaster (sorry May 4th was yesterday.) That said, when it comes to getting things done, the blaster seems more effective. I would chalk that up to garbage collection, goroutines vs async+await, and simplicity of the language in general. That said I use both languages regularly because they have different strengths and weaknesses and one is usually a clearly better option depending on the problem and requirements.
- throwaway894345 5y agoI really admire Rust iterators, especially compared to C++ iterators, but I lament that there is no easy way (that I know of, anyway) to build an iterator from a closure which yields `Option<T>`s. I don’t like that I have to define a type and implement a Trait (in general working with closures is cumbersome in Rust). That said, this isn’t a major problem either and on balance I’m very happy with Rust iterators.
- eloff 5y agoIt's probably possible to create a wrapper to do that. But if you need a closure, you can also just use a struct implementing the trait to manage the state. It's not perfect, but it's so much nicer than in C++.
- creata 5y agoMight you be looking for https://doc.rust-lang.org/std/iter/fn.from_fn.html https://doc.rust-lang.org/std/iter/fn.from_fn.html ?
- throwaway894345 5y agoOh wow, yeah, I think that’s it! Thanks very much!
- 5y ago
- edflsafoiewq 5y agoRust iterators are hard to implement without a big compile time hit.
- uh_uh 5y agoCompile time hit meaning it's difficult to get the types right or something else?
- runeks 5y agoPresumably that it’s inherently slow to compile. “Getting the types right” happens before compile time.
- masklinn 5y agoThat they rely on a lot of optimisations to be really efficient (= have any chance of approaching a regular for loop). Without that, every adapter adds a function call to the yielding of an element.
- topspin 5y agoWhat I miss in comparison to Rust is concise error handling. Rust has shown that it is entirely possible to have clear, type safe, concise error handling without try/catch rigoromol or if(err == nil) {...} pollution. My hope is that the introduction of generics in Go eventually leads to Result[] proliferating throughout golang.