谷歌应用引擎:使用Memcache还是静态变量?

21

嗯,我在这里有一个非常基本的疑问:

我正在开发一个在GAE(Java)上的应用程序,并执行一次查询以返回许多实体到数据存储区,因此我需要对其进行缓存。我之前使用了memcache,效果很好,但是如果我将实体列表保留在静态变量中,则整个请求的速度比使用memcache快了两倍。我认为这是因为我不需要一直进行实体反序列化。

使用静态变量而不是memcache会有什么缺点吗?我不知道我的应用程序在云中是否有多个实例,因此是否有多个静态变量实例?

我尝试缓存的实体列表是上周最佳(得分最高)的帖子。我会从该列表中选择5篇随机文章并在几页中显示它们。

感谢您的帮助!


3
我开始了一个实验,以找出Google App Engine(GAE)多久会提供新的Java虚拟机(JVM):http://thrdcntr.appspot.com/。 显然,在负载高时,他们会创建新的虚拟机(而不是在同一虚拟机中创建新的线程)。他们还会在一段时间后关闭未使用的虚拟机(但并不太频繁)。 - Thilo
3个回答

16

应用程序引擎通过创建新的应用程序实例来扩展,在用户数量增加时,会创建更多的实例。正如drudru所说,不同的用户可能由不同的实例提供服务。一般情况下,memcache是存储你想要全局一致的东西的最快地方。但是,在你的情况下,可能还有改进的空间。

你提到你有一个帖子列表,并随机选择5个向用户展示。如果两个不同的用户看到了不同的5个贴子,这是否重要?如果无论如何都要随机选择,也许并不重要。那么,你可以将完整的帖子列表存储在memcache中,并从memcache中获取5个随机的帖子并将它们存储在静态变量中。

其次,你具体是将什么内容存储在memcache中,并如何获取它?你是将一堆完整的帖子都存储在memcache中,然后再选择5个吗?也许你只需要下载帖子列表,选择5个,并仅获取你需要的5个?如果你认为反序列化是导致速度变慢的原因,这可能会有所帮助。在获取帖子后,你是否对帖子进行了任何处理?如果是,则该处理的结果是否可以缓存?


是的:我正在将整个帖子列表进行缓存,然后获取它们全部,再选择其中的5个。如果我只获取我想要的5个,那么速度会更快(而且更聪明!)。正如你所说,如果两个不同的用户看到不同的5个帖子也没关系。实际上,如果一个用户重新加载页面,那么这个集合将会不同,所以也许我可以继续使用静态变量?我真的不在乎有几个不同的列表实例。谢谢Peter!! - Damian
如果您想尝试获取尽可能多的性能,可以尝试使用两个级别的缓存。当请求到达时,您首先会检查静态变量缓存中是否有有效值,如果没有,则会检查memcache。如果在memcache中没有有效内容,则会从数据存储中获取数据,并填充memcache和静态变量。 - Peter Recore
1
最后一件事 - 这个操作对您的总页面加载时间有多大影响?如果您将此操作从10毫秒缩短到5毫秒,这很酷,但如果您有其他花费300毫秒的操作,您应该先集中精力处理那里 :) - Peter Recore
从我所看到的情况来看,这个操作在加载时间中占据了非常重要的一部分。谢谢Peter的回答!! - Damian

6
您不能指望静态变量(或JVM内存中的任何其他内容)在下一次请求到达时仍然存在,因为谷歌可以随意启动和停止虚拟机。从外观上看,他们似乎更喜欢启动其他JVM而不是在同一JVM中启动其他线程,这加剧了这个问题。
但是,只要您有一种从其他地方加载数据的方法,就应该能够将静态变量用作缓存层。
我也不会尝试过度使用内存,因为您可能会有可用内存的限额。

3

是的,在互联网上,无法保证您的实例对于各种用户都是相同的。在最糟糕的情况下,您可能会不断地将其读入静态内存中。使用memcache可以更高地保证可用性。我建议使用memcache,这样您的应用程序在未来就不会遇到规模问题。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接