what is nim type definition for generic procedure?
I have a strategies expressed as generics in nim:
proc fooStrategy[T](t: T, ...)
proc barStrategy[T](t: T, ...)
I would like to create a lookup table for the strategies by name... so I tried:
type
Strategy*[T] = proc[T](t: T, ...)
let strategies* = toTable[string, Strategy[T]]([
("foo", fooStrategy), ("bar", barStrategy)])
This doesn't work -- the type declaration fails. If I were to get by that I could guess that the table of strategies would also have problems. Is there another way to do this? "T" is supposed to be "some 1D collection type" -- could be sequence, array, vector from blas, etc. I could add concrete strategies to the table for common collections, but I still have the problem with the function pointer, as
type
Strategy* = proc(t: any, ...)
let strategies* = toTable[string, Strategy]([
("foo-seq[int]", fooStrategy[int]), ...])
still has problems. Any suggestions?
There are multiple issues with your code:
Firstly, initTable
does not take a list of items for the table. It only takes an initial size. You want to use toTable
instead.
Secondly, you must explicitly set a value for the generic parameter T when creating a table, because at runtime, all generic parameters must be bound to a type.
Thirdly, the proc types have to exactly match, including pragmas on the proc. This one's tricky.
Here is a working example:
import tables
type
Strategy*[T] = proc(t: T) {.gcsafe, locks: 0.}
proc fooStrategy[T](t: T) = echo "foo"
proc barStrategy[T](t: T) = echo "bar"
let strategies* = toTable[string, Strategy[int]]([
("foo", fooStrategy[int]), ("bar", barStrategy[int])
])
For this example, I create a table with Strategy[int]
values (you cannot have a table with Strategy[T]
values as this is not a concrete type). I instantiate both fooStrategy
and barStrategy
with [int]
to match the table type. I added {.gcsafe, locks: 0.}
to the type definition. If this is omitted, you will get a compiler error:
test.nim(9, 49) Error: type mismatch: got (Array constructor[0..1, (string, proc (t: int){.gcsafe, locks: 0.})])
but expected one of:
proc (pairs: openarray[(string, Strategy[system.int])]): Table[system.string, Strategy[system.int]]{.gcsafe, locks: 0.}
As you see, the compiler tells you in the first line what it sees and in the third line what it expects. it sees proc
s with {.gcsafe, locks: 0.}
because those pragmas are implicitly assigned to the proc
s defined above. The pragmas change the type, so to be able to assign those proc
s to Strategy[T]
, you have to define the same pragmas to Strategy[T]
.
上一篇: 算法的运行时间优化
下一篇: 通用程序的nim类型定义是什么?