I'm checking out Nim, have read most of the manual - there are a lot of things I like! I'm however having problems with nested template / macro / generic code, which I do not know why it doesn't work:
import iterrr
proc testIterrr() =
let m = @[1, 2, 3].items.iterrr:
max()
echo m
testIterrr()
This works when the routine is a proc or the code's outside of the routine, but not when it's a template or a generic proc, with the error deep inside iterrr macros.
My mental model is that a template is essentially copy pasting its body into callsite, with the exception that symbols can be renamed for hygene and what symbols can be early bound are early bound. AFAIK neither of these can explain the template above failing: the scope of the definition site and callsite is the same, and there are no conflicts in symbol names. What's the reason for it failing?
Another similar example, seemingly crashing the compiler:
import zero_functional
template time(runs: int, code: typed): void =
let start = cpuTime()
code
for i in 1..runs:
code
let endd = cpuTime()
echo "bench took: ", endd - start
time(1_000_000):
discard
@[1] -->
all(it mod 3 == 0)
This compiles outside of the time template, inside fails with
...........................................................................................................assertions.nim(34) raiseAssert
Error: unhandled exception: ccgtypes.nim(210, 17) `false` mapType: tyAnything [AssertionDefect]
Thanks for the help!
With this little change your second code example compiles and runs fine:
import times
template time(runs: int, code: untyped): void =