1

私はこのようなコードを持っています

def many_objects_saving(list_of_objects):
    for some_object in list_of_objects:
        # do smth with an object
        some_object.save()

私が知っているように、djangoはコードでsave()に到達するたびにデータベースにアクセスします。したがって、ここに2つの質問があります。

  1. この関数を別の関数で使用して、transaction.commit_on_successまたはtransaction.commit_manuallyデコレータでラップする場合、djangoは1つのトランザクションですべての保存を実行し、データベースへのアクセスを減らしますか(1つの関数内)?

例:

def resave_objects(model, condition):
    list_of_objects = model.objects.filter(**condition)
    many_objects_save(list_of_objects)

@transaction.commit_on_success
def many_objects_save(list_of_objects):
    for some_object in list_of_objects:
        # do smth with an object
        some_object.save()

2.もしそうなら、それは大きなクエリセットに適していますか?君たちありがとう!

4

1 に答える 1

3

すべての保存は単一のトランザクションにラッパーされますが、単一のクエリにはなりません。トランザクションを使用しても、実行するクエリの数は変わりません。

トランザクションはパフォーマンスのためではなく、データの整合性のために存在します。ビューをトランザクションでラップし、ある時点で失敗した場合 (途中のデータが間違っていて、エラーから回復できない可能性があります)、トランザクションを中止することができ、トランザクション内の以前のクエリはどれもデータベースに何らかの影響を与えます。こうすることで、失敗したリクエストによる中途半端なデータがないことを確認できます。

問題が大量の保存のパフォーマンスである場合は、一括削除/作成アプローチを使用できます。これは私のプロジェクトでの例です。アイデアは、1 つのクエリですべてのオブジェクトを削除してから、1 つのクエリですべての新しい値を再作成するというものです。すべての状況でうまくいくわけではありませんが、うまくいくかもしれません。

于 2012-11-28T10:05:32.707 に答える