2013-07-02 8 views
15

私は単純なプロパティとして状態を維持するdjangoモデルクラスを持っています。クラスにいくつかのヘルパープロパティを追加して集約状態にアクセスしました。 is_liveは、状態が['closed', 'expired', 'deleted']などの場合にfalseを返します。イディオム・パイソン - プロパティまたはメソッド?

この結果、myモデルにはis_プロパティのコレクションが含まれているため、オブジェクトの内部プロパティーについて非常に簡単な参照が行われます。

ここで、新しいプロパティー、is_completeを追加します。これは、他のすべてのプロパティーと意味的には同じですが、オブジェクトの状態をブール値でチェックします。ただし、このチェックでは、依存する(1対多)子オブジェクトの状態をチェックし、結果に基づいてレポートを返します。つまり、このプロパティは実際には複数のデータベースクエリを実行し、結果を処理します。

@propertyデコレータを使用して)プロパティとしてモデル化するのはまだ有効ですか?それとも、デコレータを先取りしてメソッドとして残すべきですか?

プロパティを使用していることは、他のすべてのプロパティと意味的に一致していることです。

これは、他の開発者に、これはより複雑な実装であることを控えていることを示しているため、控えめに使用する必要があります(つまりfor..ループ内にはありません)。

from django.db import models 

class MyModel(models.Model): 

    state = CharField(default='new') 

    @property 
    def is_open(self): 
     # this is a simple lookup, so makes sense as a property 
     return self.state in ['new', 'open', 'sent'] 

    def is_complete(self): 
     # this is a complex database activity, but semantically correct 
     related_objects = self.do_complicated_database_lookup() 
     return len(related_objects)==0 

編集:私は、もともと.NETの背景から来分割が見事に

それは間違いなく砂時計を生み出すことができ、すべてのそのコードのいずれかのチャンスがあるかどう

」、とジェフ・アトウッドによって定義されます方法でなければなりません。

EDIT 2:質問へのわずかなアップデート - 類似した名前と混合プロパティとメソッドがあるように、is_completeと呼ばれる方法、としてそれを持っている問題だろう - あるいは単に混乱を招くということでしょうか?

ので - それは次のようになります。

class SomeClass(models.Model): 
    @property 
    def is_complete(self): 
     if not hasattr(self, '_is_complete'): 
      related_objects = self.do_complicated_database_lookup() 
      self._is_complete = len(related_objects) == 0 
     return self._is_complete 

ちょうどそれ「キャッシュ」という点に注意してください。

>>> m = MyModel() 
>>> m.is_live 
True 
>>> m.is_complete() 
False 
+0

私はまだ理にかなっていると思います。結果を 'self._is_complete'としてキャッシュすることができますか?これは複数回計算されますか?計算をバックグラウンドで実行することができますか、またはプロパティが評価されるときにのみ計算が有効ですか? –

+0

@JaceBrowning:私はまったく同じ考えを持っていました(私の答えを見てください)。私はこれが大丈夫だと仮定しました(そうでなければ、いつでもクリアすることができます)。 – Tadeck

+0

@タデック:心配する必要はありません。このアプリケーションが理にかなっているかどうかを知るために 'django'について十分に知りません。 –

答えて

9

あなたが次のパターンを使用する場合は特に、それを行うために大丈夫ですその結果、最初の実行は計算を行いますが、その後は既存の結果を使用します。

+0

ありがとう@タデック - これは有効なアプローチだと思いますが、私が尋ねるべきことは、プロパティとメソッドが混在しているかどうか(同じ命名規則 - 質問2を参照)ですか? –

+0

@ HugoRodger-Brown:Pep8はメソッドとインスタンス変数の両方が 'underscore_seperate_names'という名前だと言っています。だからはい、それは絶対にうまくいきます。メソッドと変数の両方がブール値を返すので、 'is_'は接頭辞も期待しています。 – TyrantWave

+0

@TyrantWave:私は概ね同意します。さらに、良い(または平均的な)IDEは、何かがプロパティ、メソッド、または他の属性であることを伝えて適切に表示することができます。さらに、 'check_'メソッドが何も返さない(技術的には' None')か、結果を渡すコールバックを受け入れる(イベントベースのアプローチの場合)ことが期待できます。しかし、PEP8は次のように述べています。 "プロジェクト内の矛盾が重要です。モジュールまたは機能内の一貫性が最も重要です。したがって、他の人々の期待に従うよりも、一貫した図書館を持つ方が良いです。 – Tadeck

関連する問題