102

これに頭を巻くのに苦労しています。現在、次のようなモデルがいくつかあります。

 def Review(models.Model)
    ...fields...
    overall_score = models.FloatField(blank=True)

def Score(models.Model)
    review = models.ForeignKey(Review)
    question = models.TextField()
    grade = models.IntegerField()

レビューにはいくつかの「スコア」があり、overall_scoreはスコアの平均です。レビューまたはスコアが保存されたら、overall_score平均を再計算する必要があります。現在、オーバーライドされた保存メソッドを使用しています。Djangoのシグナルディスパッチャーを使用することに何か利点はありますか?

4

5 に答える 5

92

保存/削除シグナルは、問題のモデルに完全に固有ではない変更を行う必要がある場合、または共通点があるモデルに適用できる場合、またはモデル間で使用するように構成できる場合に一般的に適しています。

オーバーライドされたsaveメソッドの一般的なタスクの 1 つは、モデル内のテキスト フィールドからスラッグを自動生成することです。これは、いくつかのモデルに実装する必要がある場合、pre_saveシグナルを使用することでメリットが得られるものの例です。シグナル ハンドラーは、スラッグ フィールドの名前とスラッグを生成するフィールドの名前を取得できます。そのようなものを配置すると、配置した拡張機能はすべてのモデルにも適用されます。たとえば、問題のモデルのタイプに追加しようとしているスラッグを検索して、一意性を確保します。

再利用可能なアプリケーションは、シグナルを使用することで恩恵を受けることがよくあります。シグナルが提供する機能を任意のモデルに適用できる場合、一般的に (やむを得ない場合を除き)、シグナルの恩恵を受けるためにユーザーがモデルを直接変更する必要はありません。

たとえば、django-mpttでは、シグナルを使用しpre_saveて、作成または更新しようとしているモデルのツリー構造を記述する一連のフィールドを管理し、シグナルを使用しpre_deleteて、削除されるオブジェクトとその全体のツリー構造の詳細を削除しました。その前のオブジェクトのサブツリーとそれらは削除されます。saveシグナルを使用するため、ユーザーはモデルにメソッドを追加または変更deleteしてこの管理を行う必要はありません。管理するモデルを django-mptt に知らせるだけで済みます。

于 2008-10-05T08:38:39.653 に答える
3

シグナルを使用すると、関連するスコア モデルが保存されるたびにレビュー スコアを更新できます。しかし、そのような機能が必要ない場合、これをシグナルに入れる理由はありません。それはかなりモデル関連のものです。

于 2008-10-04T13:55:25.427 に答える
2

それは一種の非正規化です。このきれいな解決策を見てください。インプレース構成フィールド定義。

于 2008-10-04T15:21:21.230 に答える