package main
import "fmt"
var vec = []string{"the", "quick", "brown", "fox", "jumped", "over", "the", "lazy", "dog"}
func main() {
for i, s := range vec {
fmt.Printf("%d: %s\n", i, s)
}
}
Using `fmt.Println(i, ":", s)` inserts spaces on both sides of the colon, so the output is not quite right.
I find Go's `range` syntax easier to read than D's `(i, s; vec)` -- although generator functions that work with `range` have unaesthetic return types.
D has several usages for `foreach` depending on the number and type of its arguments. In this case, it sees that `vec` is an array, and so constructs a loop over the array. If `vec` was a range, the loop will be constructed as a loop over the array.
It's nice because it makes the syntax for arrays and ranges interchangeable, making for easy refactoring.
Go is similar: `for/range` has always worked on arrays, slices, maps, strings and channels, and they extended it to integers in version 1.22 and to user-defined generators in version 1.23. It generates one or two outputs depending on the type of the RHS, but one can assign the index value to _ to ignore it. Among standard types, only channels and integers generate one output; containers (including strings) give an index or key and a value.
I find Go’s version worse in that it does not allow you to elide the index (which is not needed most of the time). You have to write `for _, s := range vec`, as `for s := range vec` makes s the index.