Jos van Uden wrote: > I noticed that I don't always have to use the bang notation for > function templates. I played around with that a little, but got > an error when I used a static array. I think it's because of a > casting problem or wrong type inference... I don't imagine it's > a bug. Just not possible. > > ... > > int[20] arr4; > putNumbers(arr4, 0, 3); // ERROR, stat array, regular notation > > } > > test.d(8): Error: cast(int[])r is not an lvalue > test.d(25): Error: template instance test.putNumbers!(int[20u],int) > error instantiating
You're instantiating the template as putNumbers!(int[20u],int) because arr4 is of type int[20u]. This means Range is int[20u]. Here's the code for put: > void put(T, E)(ref T[] a, E e) { > assert(a.length); > a[0] = e; a = a[1 .. $]; > } r.put(i) is rewritten by the compiler as put(r, i)... except that put wants an int[], not an int[20u]. So it implicitly casts it to the correct type, giving put(cast(int[])r, i). But put ALSO expects its first argument to be passed by reference, and you cannot pass the result of a cast by-reference. (There are a LOT of things you can't pass by reference; it's a constant thorn in my side, and many others' sides.) The problem here is that put is fundamentally incompatible with fixed-size arrays. The solution is to change line 25 to read: auto arr4_temp = arr4[]; putNumbers(arr4_temp, 0, 3);