2012-05-14 13 views
5

私はCakePHPのリレーションシップを通して、双方向の自己参照hasManyに頭を奪おうとしています。CakePHP:双方向自己参照hasManyスルーアソシエーション

私は写真マッチングウェブサイトに取り組んでいます。

  • ピクチャは、「一致」(結合モデル)を介して他のピクチャに関連付けられます。
  • 各試合には2枚の写真があり、現在の評価と総投票数が保存されています。
  • 画像を見るときは、どちらの方向からも関連するすべての画像が(一致するものを介して)利用可能になるはずです。

私は、hasManyという関係を結合モデルと定義することから始めました。

pictures_matchesテーブルがこのような構造を持って参加する:

id | picture_id | partner_id | rating | total_votes 

私のマッチがモデル協会に参加し、次のようになります。

class PictureMatch extends AppModel { 

... 

    public $belongsTo = array(
     'Picture' => array(
      'className' => 'Picture', 
      'foreignKey' => 'picture_id', 
      'conditions' => '', 
      'fields' => '', 
      'order' => '' 
     ), 
     'Partner' => array(
      'className' => 'Picture', 
      'foreignKey' => 'partner_id', 
      'conditions' => '', 
      'fields' => '', 
      'order' => '' 
     ) 
    ); 
} 

各画像は、どちらの方向からその関連の画像にアクセスできるようにする必要があり、しかし、これは私の把握が滑っている場所です。 関係の両側を保存する必要があるように見えますが、これにより結合モデルに格納されている余分なデータが破棄されます.2つのdbエントリを使用すると、投票は方向によって異なることがあります。

誰かがCakePHPでこれを行うための最善の方法を説明することはできますか?私はむしろ混乱している。
オンザフライで逆の関係を作成することは可能ですか?

+3

あなたはこれを理解しましたか? –

+0

パートナーセクションのclassNameを「パートナー」にする必要がありますか? – khany

答えて

0

あなたはモデル:: bindModel()の上で実世界を作成することができます。これは、リバースリレーションシップをバインドしたり、その場で望む方向をバインドするのに非常に役立ちます。また、あなたは関連する日付の元をretrivingの無限連鎖を作成することができ収容可能振る舞いを使用して

http://book.cakephp.org/2.0/en/models/associations-linking-models-together.html

(「..... Picture.PictureMatch.Partner.PictureMatch.Picture」)を含ん

基本的に、あなたのモデルのすべてをループ限り、各チェーンが何らかの形で説明するために、次のいずれかに関連しているとすることができますそれより良い簡単な例(これにロジックを無視してください)

サークルbelongsToの広場 広場belongsToのトライアングル

だから、トライアングルがサークル(直接)に関連していないが、広場は

間にちょっとあります

以上の楽しみを持っている

Circle->find('all', array('...', contain => array('Square.Trinagle.Square.Circle')); 

の周りにループの円で円を得るというように、もちろんこれらの例では役に立たないと任意のプログラミングロジックなしですが、私はあなたがそのあなたができる点を理解してほしいことができますループトラフ無限の数の関係が前後しています。

0

私はこれが最善の解決策であるかどうかわからないですが、あなたがこのなかった場合:

public $belongsTo = array(
    'Picture1' => array(
     'className' => 'Picture', 
     'foreignKey' => 'picture_id', 
    ), 
    'Picture2' => array(
     'className' => 'Picture', 
     'foreignKey' => 'picture_id', 
    ), 
    'Partner' => array(
     'className' => 'Partner', 
     'foreignKey' => 'partner_id', 
    ), 
); 

をあなたが検索を行うときに、あなただけの長い間、あなたが1または2にrecursiveセットを持っているよう($this->data['Picture1'] == $var || $this->data['Picture2'] == $var)を検索し、そのすべての関連データを返すべきです。Picture

0

私はこれを放棄したが、それは簡単に解決可能だと仮定し - それはあなたのセーブが実行されている意味の参加モデル

に保存されている余分なデータが破壊され、位相

に関係していますdeleteAllと一致するレコードを挿入する代わりに、そのレコードを見つけて更新する必要があります。

これはいくつかの方法で実行できますが、最も簡単なのは保存呼び出しの前です。 priを含むマッチ・レコード・データ内のメアリー・キー。基本的にはHABTMとして保存しないでください。既に既存の一致レコードの主キー(id)を見つけようとしていて、それを保存するようにデータを更新した場合は、hasManyとして保存してください。