【发布时间】:2012-11-27 21:27:05
【问题描述】:
我有一个 Id 映射缓存占用了太多内存。它用于容纳对象的 3 种不同类型的 Id 的组合,它们的映射从表中读取,并缓存在 6 个不同的字典中,以便从任何一种 Id 类型快速查找/翻译到另一种(性能是对我的申请很重要)。
我想将其重写为内存占用更小的东西,所以我确实实现了一个 Id 的合并列表,并使用 linq/lambda 表达式来提取我想要的值。目前看起来是这样的。
public struct IdMappings
{
public int Id1;
public int Id2;
public int Id3;
}
//new cache
private static List<IdMappings> AllIdMappings = null;
//current cache implementation
private static Dictionary<int, int> Id1ToId2 = null;
private static Dictionary<int, int> Id1ToId3 = null;
//etc.
public static void FillCache(DataSet data)
{
foreach (DataRow r in data.Tables[0].Rows)
{
//fill list and/or dictionaries with id's
}
}
查询示例如下:
public static int GetId2FromId1(int id1)
{
return AllIdMappings.FirstOrDefault(m => m.Id1 == id1).Id2;
//or
return Id1ToId2[id1];
}
这在减少内存使用方面满足了我的需求,但查找性能因此受到影响,因此我正在研究如何实现不同的东西。有没有办法进行多索引键或多键查找比遍历列表相对更快?
【问题讨论】:
-
This does what I need in terms of reducing memory usage, but performance for lookups has suffered as a result- 这可能是因为您不再在内存中准备对象,因此一旦找到 ID 就需要从数据库中检索它们?即它是延迟加载而不是急切加载。您确定性能下降发生在“查找”而不是“检索”中吗? -
缓存在应用启动时被填充,所以只有一次。字典/哈希集是为快速查找而设计的,大约为 O(1)。我确实相信使用带有 linq 的列表将始终是 O(n),因为它会遍历整个列表以找到匹配项。
-
如果这是对我的评论的回应,当您说“缓存已满”时,您是指
objects还是keys?如果您预先检索对象,您不妨创建一个对象字典而不是它们的键 - 没有内存优势。而如果你不检索对象,那么在找到合适的键后,你需要从数据库中获取相应的对象,这将导致更长的执行时间。
标签: c# linq search .net-4.0 lookup