Great write-up.
> Keyword arguments should be added to the language. In idiomatic Go, we often use struct literals (together with "make the zero value useful", e.g. allocate map-typed fields lazily) instead of object-creation functions: x := &FooBar{ A: a, B: b.c(), } instead of x = newFooBar(A=a, B=b.c()) Either way, you get the "A", "B" names at the 'call site'. For example, the https://golang.org/pkg/io/#LimitedReader struct just exports its fields, and you use it like this (https://go.googlesource.com/go/+/refs/heads/master/src/io/io_test.go#39). There is no io.NewLimitedReader function. > True iterators are felt by their absence and would be easy to add. If you really want lazy lists, I'd use a generating function (a closure) instead of slices. It seems to me that that's what you discuss in your "Iterator variant A" example, so I'm not exactly sure what you're asking for? New rules for the built-in "range" keyword?? But iteration can already be: ``` it := foobar.iterator() for x := it(); x != nil; x = it() { etc(x) } ``` which doesn't seem so onerous to require changing the language. To map a function f isn't as terse as a Python list comprehension, but it's still easy: ``` it := foobar.iterator() for x := it(); x != nil; x = it() { fx = f(x) etc(fx) } ``` > A technical writer with an outside-in view of the language should be hired on > to do an edit pass and reorganization of the documents. Out of curiosity, have you looked at "The Go Programming Language" book by Donovan and Kernighan? It's the same K as in K&R's "The C Programming Language", which is generally regarded as excellent language documentation. On a related point: > I got substantial help understanding interfaces from an old blog post by Ian > Lance Taylor If it's https://research.swtch.com/interfaces then the blog post author is Russ Cox, not Ian Lance Taylor. > Lookbehinds should be added to the regexp library. See https://groups.google.com/d/msg/golang-nuts/7qgSDWPIh_E/OHTAm4wRZL0J Other thoughts below... ---- The idiomatic form of ``` switch child.(type) { case *Commit: successorBranches.Add(child.(Commit).branch) } ``` is: ``` // Yes, the inner 'child' deliberately shadows the outer 'child'. switch child := child.(type) { case *Commit: // Here, 'child' has the concrete type, not the interface type. successorBranches.Add(child.branch) } ``` ---- ``` func pipeline(source T) error { { result1, err1 := transform1(source) if err1 != nil { return err } result2, err2 := transform2(result1) if err2 != nil { return err } result3, err3 := transform3(result2) if err3 != nil { return err } return nil } ``` Is indeed "eyeball friction". That's the motivation for https://github.com/golang/proposal/blob/master/design/32437-try-builtin.md, which would make it: ``` func pipeline(source T) error { { result1 := try transform1(source) result2 := try transform2(result1) result3 := try transform3(result2) return nil } ``` For much, much more discussion (too much) see https://github.com/golang/go/issues/32437 -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/CAOeFMNUyWOXpFo6w8DL%3D7WMNGjXAvCc-rd8uSH8DXPyy9cY5zg%40mail.gmail.com.