MemoryCache范围会话还是应用程序范围?

时间:2013-05-21 20:28:02

标签: asp.net caching memorycache

我在ASP.NET中使用MemoryCache并且运行良好。我有一个缓存了一个小时的对象,以防止从存储库中获取新的数据。

我可以看到缓存在调试中工作,但是一旦部署到服务器,在第一次调用并且缓存了对象之后,后续调用大约是1/5的时间。

但是我注意到每个新的客户端呼叫(仍然在1小时窗口内 - 实际上只是一分钟或2分钟后)似乎第一次调用我的服务(这是做的缓存)在缓存数据之前几乎与原始调用一样长。

这让我开始怀疑 - 特定于MemoryCache会话,并且每个进行调用的新客户端都存储它自己的缓存,或者是其他一些事情导致第一次调用甚至 之后我知道数据已被缓存了吗?

2 个答案:

答案 0 :(得分:69)

来自MSDN

  

Cache和MemoryCache类之间的主要区别是   MemoryCache类已被更改为可供.NET使用   不是ASP.NET应用程序的框架应用程序。例如,   MemoryCache类与System.Web程序集没有依赖关系。   另一个区别是你可以创建多个实例   MemoryCache类用于相同的应用程序和相同的应用程序   AppDomain实例。

阅读并在反射代码中进行一些调查显然MemoryCache只是一个简单的类。您可以使用MemoryCache.Default属性(重新)使用相同的实例,也可以根据需要构建任意数量的实例(尽管建议的实例尽可能少)。

所以基本上答案就在于你的代码 如果您使用MemoryCache.Default,那么只要您的应用程序池存在,您的缓存就会存在。 (只是提醒您默认应用程序池空闲超时是20分钟,不到1小时。)

如果使用new MemoryCache(string, NameValueCollection)创建它,则上述注意事项以及您创建实例的上下文,即如果您在控制器中创建实例(我希望不是这种情况),那么您的缓存会存在一个请求

很遗憾我找不到任何引用,但是...... MemoryCache不保证根据您指定的缓存策略保存数据。特别是如果您运行应用程序的计算机在内存上受到压力,您的缓存可能会被丢弃。

如果您仍然没有运气确定早期缓存项目失效的原因,您可以利用RemoveCallback并调查项目失效的原因。

答案 1 :(得分:25)

一年后回顾这一点,我在原帖上发现了一些关于缓存“随机丢弃”的更多信息。 MSDN对可配置缓存属性CacheMemoryLimitMegabytesPhysicalMemoryLimitPercentage

说明以下内容
  

默认值为0,表示MemoryCache类   默认使用自动调整启发式算法。

进行一些反编译和调查,CacheMemoryMonitor.cs类中存在定义内存阈值的预定场景。以下是AutoPrivateBytesLimit属性中该类注释的示例:

// Auto-generate the private bytes limit:
// - On 64bit, the auto value is MIN(60% physical_ram, 1 TB)
// - On x86, for 2GB, the auto value is MIN(60% physical_ram, 800 MB)
// - On x86, for 3GB, the auto value is MIN(60% physical_ram, 1800 MB)
//
// - If it's not a hosted environment (e.g. console app), the 60% in the above
//   formulas will become 100% because in un-hosted environment we don't launch
//   other processes such as compiler, etc.

特定的值并不一定与实现为何经常使用缓存一样重要:存储我们不想获取的大型对象并结束。如果这些大型对象存储在缓存中,并且超出了基于这些内部计算的托管环境内存阈值,则可以自动从缓存中删除该项。这当然可以解释我的OP,因为我在托管服务器上存储了一个非常大的集合,可能有2GB的内存在IIS中运行多个应用程序。

设置这些值有明确的覆盖。您可以通过配置(或在设置MemoryCache实例时)设置CacheMemoryLimitMegabytesPhysicalMemoryLimitPercentage值。以下是MSDN链接的修改示例,其中我将physicalMemoryPercentage设置为95(%):

<configuration>
  <system.runtime.caching>
    <memoryCache>
      <namedCaches>
          <add name="default" 
               physicalMemoryLimitPercentage="95" />
      </namedCaches>
    </memoryCache>
  </system.runtime.caching>
</configuration>
相关问题