我想在软实时环境中使用Nim,其中内存分配和垃圾收集都表现出太多的延迟。因此,手动内存管理是理想的 - 或者甚至更好,只能从堆栈内存中工作。
我可以使用哪个Nim子集来实现堆栈内存分配?我猜我可以通过缓存的C代码中缺少memset或memcpy来判断它是否有效。
答案 0 :(得分:3)
如果你真的想要没有垃圾收集,你需要使用--gc
none
参数,如Nim Compiler User Guide中所述。 none
参数禁用垃圾收集器,让您自己独立。这通常意味着任何字符串操作都会产生警告,因为尽管分配了内存,但没有人会在以后释放它:
proc main() =
let x = 5
echo "Hello " & $x & " there"
main()
如果使用nim c --gc:none -r test.nim
编译此小测试,您将收到gc警告:
test.nim(3, 19) Warning: '$ x' uses GC'ed memory [GcMem]
test.nim(3, 22) Warning: '&("Hello ", $ x, " there")' uses GC'ed memory [GcMem]
这可以帮助您直接或间接地在无GC环境中捕获Nim的安全部分。但请注意,某些操作可以移动到编译阶段。因此,以下示例生成相同的输出在没有GC的情况下可以安全使用,因为所有const
表达式都是由生成的C代码静态分配的:
proc main() =
const x = 5
echo "Hello " & $x & " there"
main()
查看nimcache
目录,您会发现源代码包含与此类似的行:
STRING_LITERAL(TM_ipcYmBC9bj9a1BW35ABoB1Kw_2, "Hello 5 there", 13);
请注意,在上面提到的文档中,有一个指向Nim's Garbage Collector文档的链接,其中包含一个非常具体的实时支持部分,可能会有所帮助,并且可能会避免如果它提供的妥协符合您的要求,则需要手动处理内存。
答案 1 :(得分:0)
目前,字符串和seq类型都要求GC正常工作,即使它们具有值类型语义。然而,这计划改变。我不能告诉你这是什么时候。如果没有这两种类型,Nim实际上并不是您想要使用的语言。除了类型之外,它几乎与c ++类似。因此,如果您不使用ref
类型,则无法为GC进行进一步分配。
答案 2 :(得分:0)
不是Nim的细节,既不是GC的细节,也不是我在这里提供合理的答案,而是与语言无关的编程建议。
在Android上,堆栈是有限的,MiB或24KiB。您可以通过左右调整清单来制作8MiB。
如果您没有操作系统,请使用实模式和非虚拟化的内存空间,也许你将拥有无限的堆栈。
但是大多数真实世界的应用程序都必须使用分配器。在堆上保留一块内存,并保留一个可以手动递增/递减的自定义“堆栈指针”,相比之下通常让编译器执行此操作。
这带来了两个优点:从调用堆栈和块范围中解耦。和无限的记忆。
限制:在Linux上,您的页面将根据需要填充零。内核懒惰地提供页面,因此您将在关键时刻体验到口吃。为避免这种情况,请在整个空间准备一次写入0xff的扫描通道。 这样做的缺点是与其他进程非常不合作,并且可能会破坏文件系统缓存。但对于通常被用户接受的实时应用程序。