2011-01-30 10 views
2

をフィルター1つのベースクエリセットに異なる時間を複数のフィルタを実行するとジャンゴDBアクセスの最適化:あなたは、私がこのような何かを行うビューを持っている日付範囲

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の

を使用しています

とにかく、私はobjectBaseをフィルタリングして日付でフィルタリングする必要がある約20種類の方法があり、それぞれのSQLクエリが日付順にフィルタリングされていることに気付きました。後続のクエリを日付でフィルタリングする必要がないようにする効率的な方法はありますか?スピードの違いはありますか?

また、理論的には、フィルタリングされた日付と開始日の可能性のあるフードの数百または数千のオブジェクトを保持できるため、objectBaseクエリをキャッシュするための最良の方法と思われます。非常にありそうもない。

は、いくつかの重複があるので、ここでT1 < T3 < T2及びT2 < T4 T4に後で要求T3次に誰かが日付T1およびT2の間の統計情報を要求することができると言う、等が挙げられます。それをキャッシュする方法はありますか?それは、そこにデータベースにアクセスする必要がある要求の間に重複がありますか?

ご迷惑をおかけして申し訳ございませんが、ご迷惑をおかけして申し訳ございませんが、ご了承ください。クエリの数を減らすために

答えて

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を作成してもデータベースはヒットしません。 dbからすべてのオブジェクトを取得し、それらをpython/django経由でキャッシュすると、多くのメモリが消費され、パフォーマンスが低下する可能性があります。データベース/ SQLクエリを使用してカウントを行うのは、結果を得るための最速の方法です。