41

PHP Doctrine ORM を使用してクエリを作成しています。しかし、DQL (Doctrine Query Language) を使用して次の WHERE 句を記述する方法がよくわかりません。

WHERE name='ABC' AND (category1 = 'X' OR category2 = 'X' OR category3 = 'X') 
AND price > 10

括弧の位置を指定するにはどうすればよいですか?

私が現在PHPコードに持っているのはこれです:

->where('name = ?', 'ABC')
->andWhere('category1 = ?', 'X')
->orWhere('category2 = ?', 'X')
->orWhere('category3 = ?', 'X')
->andWhere('price > ?', 10)

しかし、これは次のようなものを生成します

WHERE name='ABC' AND category1 = 'X' OR category2 = 'X' OR category3 = 'X' 
AND price > 10

操作の順序が原因で、意図した結果が返されません。

また、「where」、「andWhere」、および「addWhere」メソッドに違いはありますか?

UPDATE わかりました、DQL を使用して複雑なクエリを実行することはできないようです。そのため、手動で SQL を記述し、andWhere() メソッドを使用して追加しようとしています。ただし、私は WHERE..IN を使用しており、Doctrine は囲み括弧を削除しているようです:

$q->andWhere("(category1 IN $subcategory_in_clause
            OR category2 IN $subcategory_in_clause 
            OR category3 IN $subcategory_in_clause)");
4

7 に答える 7

73

私の経験から、各複雑なwhere関数は括弧内にグループ化されています(私はDoctrine 1.2.1を使用しています)。

$q->where('name = ?', 'ABC')
  ->andWhere('category1 = ? OR category2 = ? OR category3 = ?', array('X', 'X', 'X'))
  ->andWhere('price < ?', 10)

次のSQLを生成します。

WHERE name = 'ABC' 
  AND (category1 = 'X' OR category2 = 'X' OR category3 = 'X')
  AND price < 10
于 2010-01-11T02:18:32.427 に答える
25

これを行う正しい方法は、教義 2 - クエリ ビルダーの条件付きクエリ... If ステートメントで見つけることができます。@Jekisが指摘したように。@anushrの例のように、式ビルダーを使用してこれを解決する方法は次のとおりです。

$qb->where($qb->expr()->eq('name', ':name'))
  ->andWhere(
    $qb->expr()->orX(
      $qb->expr()->eq('category1', ':category1'),
      $qb->expr()->eq('category2', ':category2'),
      $qb->expr()->eq('category3', ':category3')
  )
  ->andWhere($qb->expr()->lt('price', ':price')
  ->setParameter('name', 'ABC')
  ->setParameter('category1', 'X')
  ->setParameter('category2', 'X')
  ->setParameter('category3', 'X')
  ->setParameter('price', 10);
于 2016-08-18T17:12:18.703 に答える
1

andWhere は次のように要約できます。
以前に追加された条件を認識した WHERE ステートメント

whereの代わりにandWhereを安全に使用できます。(これにより、以下の 2 番目のリスト項目に記載されている非常に小さなオーバーヘッドが発生します。)

andWhere の実装は: (Doctrine 1.2.3)

public function andWhere($where, $params = array())
{
    if (is_array($params)) {
        $this->_params['where'] = array_merge($this->_params['where'], $params);
    } else {
        $this->_params['where'][] = $params;
    }

    if ($this->_hasDqlQueryPart('where')) {
        $this->_addDqlQueryPart('where', 'AND', true);
    }

    return $this->_addDqlQueryPart('where', $where, true);
}

これは次のように読むことができます。

  1. プロセスパラメータ
  2. 別の where ステートメントが前に追加された場合、クエリのwhere部分にANDステートメントを追加します。
  3. 追加条件
于 2011-02-05T09:37:13.237 に答える
0

where、andwhere、および addwhere の違いについては、最後にソースを読んだときと大きな違いはないと思います。ただし、Doctrine のソースを読むことをお勧めします。とてもシンプルで、ドキュメントの穴を埋めるのに役立ちます (たくさんあります)。複雑な where ステートメントについては、私自身も疑問に思っていましたが、まだその必要はありませんでした。

于 2009-06-26T15:09:21.420 に答える
0

私の経験では、次の違いが見られることがあります。

$q->andWhere("(category1 IN $subcategory_in_clause
            OR category2 IN $subcategory_in_clause 
            OR category3 IN $subcategory_in_clause)");

$q->andWhere("(category1 IN $subcategory_in_clause OR category2 IN $subcategory_in_clause OR category3 IN $subcategory_in_clause)");

最初のステートメントは 3 行で記述され、2 番目のステートメントは 1 行で記述されます。信じられませんでしたが、違いがあります。

于 2014-03-05T09:58:01.473 に答える