我有一个KDB / Q数据库,每天大约有2M的记录消耗大约2G的内存。在一天结束时,它会运行一些报表,在表之间进行连接并将结果输出到磁盘上的文件中。在计算过程中,内存使用量增长到~15G。我的问题是,一旦此操作完成,内存永远不会被释放,直到DB重新启动它消耗所有15G的内存。
我想告诉KDB从内存中卸载一些表(虽然不要删除它们)但我不想重启数据库,因为其他一些应用程序仍在连接它。
有没有办法告诉KDB从内存中卸载某些东西?
修改
如果有人觉得有趣,我建议您查看.Q.gc[]
的KDB 2.5+,看起来很有希望。
答案 0 :(得分:9)
以下是我的研究总结:
.Q.gc[]
调用,这是对垃圾收集器的请求调用(KDB使用ref。计数btw。)答案 1 :(得分:5)
这可能是显而易见的,但除了检查q版本的垃圾收集模式之外,请确保您实际上已经删除了使用内存的内存数据。如果你没有摆脱整个表(例如,这是计算中涉及的临时表),只需从根命名空间中删除它
delete table from`.
如果没有,您可以删除其所有行
delete from`table
答案 2 :(得分:3)
对于今后尝试此操作的任何人来说,最简单的方法是:
如上述海报所述,较新版本的KDB可以更好地释放内存但不完美。
我们公司网站上有一篇很好的文章详细介绍了KDB +内存管理: http://timestored.com/kdbGuides/memoryManagement
答案 3 :(得分:1)
http://code.kx.com/q4m3/12_Workspace_Organization/#125-expunging-from-a-context
我使用了一些不同的命令。只要你的表存储在磁盘上就可以清除它,你应该没问题。
这是创建表格之前的会话。
q).Q.w[]
used| 290192
heap| 67108864
peak| 67108864
wmax| 0
mmap| 0
mphy| 8589934592
syms| 629
symw| 20704
此命令创建表,然后将其保存到磁盘。
q)t:([]10000?"ab"; 10000?5)
q)save `t
`:t
该表仍在内存中
q).Q.w[]
used| 437808
heap| 67108864
peak| 67108864
wmax| 0
mmap| 0
mphy| 8589934592
syms| 629
symw| 20704
让我们从内存和垃圾收集中删除变量。
q)delete t from `.
`.
q).Q.gc[]
0
现在使用的内存已经减少到类似于会话开始的数量。
q).Q.w[]
used| 290208
heap| 67108864
peak| 67108864
wmax| 0
mmap| 0
mphy| 8589934592
syms| 630
symw| 20730
q)\v
`symbol$()