2011-01-30 38 views
2

我有一个做了这样的观点进行多重过滤不同时间的Django DB访问:优化,当你在一个基地的QuerySet被过滤的日期范围

objectBase = MyModel.objects.filter(startDate__range=(start,end)) 
automatedObjects = objectBase.filter(automated = True).count() 
userCreatedObjects = objectBase.filter(userCreated = True).count() 
bookObjects = objectBase.filter(subClass = 'book').count() 
pageObjects = objectBase.filter(subClass = 'page').count() 
allObjectsCount = objectBase.count() 

我使用1.2.4和最新的Postgres

不管怎么说,我有大约20种不同的方式来过滤我过滤日期的objectBase,并且我注意到每个SQL查询按日期过滤。有没有更有效的方法使后续查询不必按日期过滤?会有速度差吗?

另外你认为什么是缓存objectBase查询的最佳方法,因为理论上它可以容纳数百或数千个过滤日期的对象以及可能的启动引擎,结束日期对于请求是相同的非常不可能。

好比说有人可以请求T4日期t1和t2,再后来要求T3之间的统计其中T1 < T3 < T2和T2 < T4,从而有一些重叠。有没有办法将它缓存起来,以便在需要访问数据库的请求之间有重叠?

对不起,如果这似乎是一个沉重的要求,但任何帮助,将不胜感激。

回答

0

为了减少查询的次数......

objectBase = MyModel.objects.filter(startDate__range=(start,end)) 
automated, user_created, books, pages, total = 0,0,0,0,0 
for o in objectBase: 
    if o.automated: automated += 1 
    if o.userCreated: user_created += 1 
    if o.subClass == 'book': books += 1 
    if o.subClass == 'page': pages += 1 
    total += 1 

这将只执行一个查询,但它可能会比你已经做什么,取决于你的SQL索引慢。如果您指向的所有字段都已编入索引,并且日期范围一致,那么您的解决方案将很快。然而,我怀疑你将所有这些字段编入索引。

对你的缓存问题。没有简单的方法来缓存查询集结果而不使用相同的查询集实例。您可以尝试使用django缓存框架,但是如果您的表中有成千上万行,我认为缓存不会帮助您。

我的建议是创建日期范围所涵盖的所有列的索引。这应该使您的.count查询速度非常快,而无需遍历可能的大量集合。

0

你正在做的,除非你遇到一些沉重的性能问题应该是罚款的方式。创建查询集objectBase不会命中数据库,因为查询尚未执行。从数据库检索所有对象并通过python/django缓存它们可能会消耗大量内存并降低性能。通过数据库/ sql查询进行计数应该是获得结果的最快方法!