我需要一个大型的数据列表,当在特定位置引用时,这些数据列表将计算(从文件加载和/或在尚未生成的情况下生成它)并保留以供将来使用。这是由绑定到函数的惰性列表驱动的。这些“块”有时会被加载,但之后从未真正被使用过,同时仍然在代码中被有效地引用,所以GC不会接受它们。Haskell惰性卸载
由于RAM快速填满,我想懒惰地卸载这些块一段时间后,他们什么都不用。这可能吗?
我需要一个大型的数据列表,当在特定位置引用时,这些数据列表将计算(从文件加载和/或在尚未生成的情况下生成它)并保留以供将来使用。这是由绑定到函数的惰性列表驱动的。这些“块”有时会被加载,但之后从未真正被使用过,同时仍然在代码中被有效地引用,所以GC不会接受它们。Haskell惰性卸载
由于RAM快速填满,我想懒惰地卸载这些块一段时间后,他们什么都不用。这可能吗?
您可以通过使用unsafeInterleaveIO
读取数据块,并定期通过该列表会并消除了未使用的很长一段时间(或者大块的引用实现这个:使用弱指针作为@nponeccop建议在评论),但我会选择一些不依赖GC来管理块的内存(因为可预测的内存使用情况对您很重要)。
例如:
import Data.HashTable.IO
type ChunkMap = BasicHashTable ChunkId (Maybe Chunk)
newChunkMap :: IO ChunkMap
getChunk :: ChunkMap -> IO Chunk
freeUnusedChunks :: ChunkMap -> IO()
其中getChunk
分配用于与malloc
和freeUnusedChunks
丢失块存储器通过表和free
小号未使用组块去。
你甚至可以运行在单独的线程freeUnusedChunks
:
freeThread = forever $ do
withChunkMapLock $ do
freeUnusedChunks map
threadDelay 5000000
我怎么知道哪些不被使用? – kvanberendonck
将时间戳与每个块关联并在每次访问时对其进行更新。然后,您可以将最后N个时间戳保留在循环缓冲区中,或者使用'freeUnusedChunks'计算它们。 –
弱指针(来自'base'的'System.Mem.Weak')怎么办?它们在这里适合吗? – nponeccop
你所说的“懒卸”是什么意思?直到最后一刻才卸载? –