2009-08-10 48 views
2

我试图在传统的ASP站点中实现不同的缓存实现,以便在繁忙流量期间卸载数据库。在传统的ASP内存泄漏中实现对象缓存

我的做法是这样的:

,我后来在商店的JScript对象中

<object id="SIZE_LIST" progid="System.Collections.HashTable" runat="Server" scope="Application"></object> 

这给了我一个哈希表全球对象创建Global.asa中的一个全局Hashtable对象,我以特定的时间间隔替换HashTable的内容。大小只会有所不同,但我会做。每次删除()和.Add()所有对象。

这很有效,除此之外,经过一段时间后,应用程序的内存分配会变得很高,从而导致会话的非理性行为。它会“忘记”会话,但不会在global.asa中调用OnSessionStart()。因此,为访客留下一个空的会话集合。

我能以某种方式改善内存重新分配过程吗?有没有更好的对象缓存方法?

我曾尝试使用纯文本文件与json序列化的数据,但反序列化的是很多开销。我想过二进制序列化,但我不确定在传统的ASP中是否有可能。

回答

1

与常规的“Scripting.Dictionary”相比使用.NET HashTable的原因是什么?

当你做传统的ASP时,为什么普通的COM对象不够用?

+0

afaik Scripting.Dictionary和IISSample.LookupTable绑定到它们只能存储原始数据类型(字符串和数字)的事实。这会让我再次需要序列化。当然,我不需要反序列化所有的东西。 LookupTable也不支持动态变化(我知道我们有Scripting.Dictionary的问题,但我不能肯定地说) – jishi 2009-08-11 07:25:39

+0

我想这是问题:http://www.4guysfromrolla.com /aspfaqs/ShowFAQ.asp?FAQID=129 – jishi 2009-08-11 07:30:55

+0

Scripting.Dictionary可以存储您喜欢的任何值。对象引用*和*原始值。仅限制:键必须是字符串。 – Tomalak 2009-08-11 08:54:01

0

不要试图重新发明轮子。使用memcache。它免费且易于安装。作为奖励有ttl(生存时间)和超出服务器边界的作品

+0

从我所学到的,memcached需要至少2个单独的服务器。这对于像这样简单的任务来说是一个相当大的设置。它也是基于网络的,意味着比将其存储在RAM中的开销更大。当然,正如你所说,更具可扩展性,如果我创建1个设置,我可以将它用于多个站点,但我不确定在不久的将来我是否有这种需求。 – jishi 2009-08-11 07:27:58

+0

memcache可以在同一台机器上运行。你是对的,有点开销。但与不必每次再次查询的收益相比,这是微不足道的。 – Toad 2009-08-11 08:32:13

0

这只是一个猜测,但它可能是因为你将JScript对象存储到.net哈希中,你仍然可以保留对该对象垃圾收集从来没有得到正确完成其工作的机会。

我以前使用过JSON字符串的应用程序,在重新提供数据时快速地进行处理和评估。

如果您担心数据过期,可以使用XMLHTTPRequest服务器端(令人惊讶的快速)调用aspx页面,该页面将执行搜索并返回JSON字符串。 aspx页面可以使用.net奇妙的缓存为您处理缓存,甚至可以使用SharpZipLib压缩JSON字符串,然后将其存储在缓存中,以便更多地减少内存占用。这也是将XML文件存储在缓存中的一个很好的技巧(600K在0.0016秒内降至25K!)

我们以前在项目中使用过上述所有项目,但并不完美,但是基于限制和遗留代码。而且它们都非常快速(不是由.net标准确定,而是为了真正快速地编写脚本)。

+0

好吧,当我们尝试在应用程序中存储json字符串时,我们遇到了相同的内存问题。即使eval速度非常快,但在CPU上也非常激烈。我们也用SessionStart的东西得到了这个奇怪的行为。这一切都取决于我们在这种情况下存储在Application中的数据量,所以它看起来似乎无懈可击,或者我们做错了什么。 当w3wp.exe开始使用大约300MB时,我们开始为某些访问者获取这个间歇性问题。 – jishi 2009-08-11 14:11:02

+0

如果CPU的密集程度在这里或那里不是那么高,那么CPU的密集程度就没有问题了。是的,你正在做的工作太多了,你将不得不重新审视这个解决方案。可能是因为你试图对缓存做太多的工作。你真的需要缓存一切吗?如果你这样做,那么你可能必须走建设自定义函数的路线来从应用程序重建对象而不是评估它们(参见http://stackoverflow.com/questions/1196525/classic-asp-store-objects-in-the -session对象/ 1206639#1206639)。我知道你说过你不想这样做,但你现在的选择是有限的 – 2009-08-12 11:34:52

0

我会选择更低技术的方法,并将每个对象(与字符串键)分开存储在Application对象中。这样你就不会从脚本引擎的角度看到一个巨大的对象。你认为这会有所帮助吗?

+0

尝试过了,搞乱Application也不是一个好主意。从应用程序连续写入/读取往往会耗尽所有内存和会话垃圾的麻烦。 – jishi 2009-12-30 15:12:08