1

私がやろうとしていること:

他のテーブルにも結合しているテーブルに対して、harsine 計算を使用してクエリを実行する

何が問題なのですか:

ORMレベルでの関連付けは、私が試みているアプローチでは機能していない/適切に水和していないようです.

詳細

関連するコードをすべて切り取ると、この質問は巨大になるので、関連するものにとどめようとします。

まず、クエリ対象のプライマリ テーブルのアソシエーション マッピングは次のとおりです

/**
 * @var IssueType $type
 *
 * @ORM\ManyToOne(targetEntity="IssueType")
 * @ORM\JoinColumn(name="type_id", referencedColumnName="id")
 */
protected $type;

注: 実際には他に 4 つの関連付けられたテーブルがありますが、上記のテーブルは「最初に失敗」しているため、この問題を解決できれば残りのテーブルも解決できると期待しています。

今、この記事から直接作業し、ここからいくつかのヒントを得て、指定された地理的半径内の問題テーブルからデータを取得しようとしています。しかし、記事の例とは異なり、私のデータは 1 つのテーブルでフラットではありません。IssueRepositoryクラスにカスタム ファインダーを入力します。

public function findNear( $em, $point, $radius=1 )
{
  $rsm = new ResultSetMapping();

  $rsm->addEntityResult('MyBundle:Issue', 'i');
  $rsm->addFieldResult('i', 'id', 'id');
  $rsm->addFieldResult('i', 'title', 'title');
  $rsm->addFieldResult('i', 'detail', 'detail');
  $rsm->addFieldResult('i', 'lat', 'lat');
  $rsm->addFieldResult('i', 'lng', 'lng');

  $rsm->addJoinedEntityResult('MyBundle:IssueType' , 't', 'i', 'type');
  $rsm->addFieldResult('t', 'name', 'name');

  $query = $em->createNativeQuery(
    "SELECT i.*
          , ( 3959 * acos( cos( radians(?) ) * cos( radians( i.lat ) ) *
            cos( radians( i.lng ) - radians(?) ) + sin( radians(?) ) *
            sin( radians( i.lat ) ) ) ) AS distance
          , t.name as type_name
       FROM issue i
       LEFT JOIN issue_type t
         ON i.type_id = t.id
      GROUP BY i.id, t.name
     HAVING ( 3959 * acos( cos( radians(?) ) * cos( radians( i.lat ) ) *
            cos( radians( i.lng ) - radians(?) ) + sin( radians(?) ) *
            sin( radians( i.lat ) ) ) ) < ?
      ORDER BY distance"
    , $rsm
  );

  $query->setParameter( 1, $point->lat );
  $query->setParameter( 2, $point->lng );
  $query->setParameter( 3, $point->lat );
  $query->setParameter( 4, $point->lat );
  $query->setParameter( 5, $point->lng );
  $query->setParameter( 6, $point->lat );
  $query->setParameter( 7, $radius, Type::INTEGER );

  return $query->getResult();
}

今は少し面倒ですが、これを機能させようとしています。このクエリから返されたデータはIssueType、オブジェクトから関連付けを取得しようとするとすぐに失敗しIssueます。

foreach ( $issues as $issue )
{
  // Fails, since Issue::getType() returns NULL
  echo $issue->getType()->getName();
}

これにより、

「非オブジェクトでのメンバー関数 getName() の呼び出し」

エラー。

さて、私は Doctrine2 の内部構造をよく知らないので、この ResultSetMapping ベースのクエリが、通常 ORM を介して実行するクエリとどのように異なるのかわかりません。

誰か光を当てることができますか?

バージョン

  • PHP: 5.4
  • PostgreSQL: 9.1
  • Symfony: Symfony 2.1
  • ドクトリン: 2.3
4

1 に答える 1

1

おそらく(確かではありませんが)「メタ列」について説明する必要があります。

$rsm->addMetaResult('i', 'type_id', 'type');
于 2012-09-27T22:53:20.657 に答える