web-dev-qa-db-ja.com

codeigniterアクティブレコードパターンを使用したUNIONクエリ

PHP CodeIgniterフレームワークのアクティブレコードクエリ形式でUNIONクエリを実行するには?

28
strike_noir

CodeIgniterのActiveRecordはUNIONをサポートしていないため、クエリを記述してActiveRecordのクエリメソッドを使用するだけです。

$this->db->query('SELECT column_name(s) FROM table_name1 UNION SELECT column_name(s) FROM table_name2');
34
Zack

これは私がかつて使用した迅速で汚い方法です

// Query #1

$this->db->select('title, content, date');
$this->db->from('mytable1');
$query1 = $this->db->get()->result();

// Query #2

$this->db->select('title, content, date');
$this->db->from('mytable2');
$query2 = $this->db->get()->result();

// Merge both query results

$query = array_merge($query1, $query2);

私の最高の仕事ではありませんが、それは私の問題を解決しました。

注:結果を注文する必要はありませんでした。

22
afinno

Last_query()を使用して結合を行うと、アプリケーションのパフォーマンスが低下する場合があります。シングルユニオンの場合、3つのクエリを実行する必要があるためです。つまり、「n」ユニオン「n + 1」クエリの場合。 1-2クエリの結合にはあまり影響しません。しかし、多くのクエリや大きなデータを持つテーブルを結合すると問題が生じます。

このリンクは非常に役立ちます: アクティブなレコードのサブクエリ

アクティブレコードと手動クエリを組み合わせることができます。例:

// #1 SubQueries no.1 -------------------------------------------

$this->db->select('title, content, date');
$this->db->from('mytable');
$query = $this->db->get();
$subQuery1 = $this->db->_compile_select();

$this->db->_reset_select();

// #2 SubQueries no.2 -------------------------------------------

$this->db->select('title, content, date');
$this->db->from('mytable2');
$query = $this->db->get();
$subQuery2 = $this->db->_compile_select();

$this->db->_reset_select();

// #3 Union with Simple Manual Queries --------------------------

$this->db->query("select * from ($subQuery1 UNION $subQuery2) as unionTable");

// #3 (alternative) Union with another Active Record ------------

$this->db->from("($subQuery1 UNION $subQuery2)");
$this->db->get();
20
Somnath Muluk

次のメソッドを使用して、モデル内のSQLステートメントを取得できます。

$this->db->select('DISTINCT(user_id)');
$this->db->from('users_master');
$this->db->where('role_id', '1');

$subquery = $this->db->_compile_select();
$this->db->_reset_select();

これにより、SQLステートメントは実際には実行されずに、$ subquery変数に格納されます。

あなたはずっと前にこの質問をしたことがあるので、おそらくあなたはすでに答えを得ているでしょう。そうでない場合、このプロセスがトリックを行う可能性があります。

8
Souvik

ActiveRecordスタイルでUNIONを追加するのにうまく機能したこのライブラリを見つけました。

https://github.com/NTICompass/CodeIgniter-Subqueries

ただし、最初にCodeIgniterのdevブランチからget_compiled_select()メソッドを取得する必要がありました(ここで入手可能: https://github.com/EllisLab/CodeIgniter/blob/develop/system/database/DB_query_builder .php -DB_query_builderはDB_active_recを置き換えます。おそらく、このメソッドはCodeIgniterの将来の製品リリースで利用可能になるでしょう。

System/databaseのDB_active_rec.phpにそのメソッドを追加すると、魅力的に機能しました。 (これはプロダクションアプリであるため、CodeIgniterの開発バージョンを使用したくありませんでした。)

2
Matt Browne

これを試して

function get_merged_result($ids){                   
    $this->db->select("column");
    $this->db->distinct();
    $this->db->from("table_name");
    $this->db->where_in("id",$model_ids);
    $this->db->get(); 
    $query1 = $this->db->last_query();

    $this->db->select("column2 as column");
    $this->db->distinct();
    $this->db->from("table_name");
    $this->db->where_in("id",$model_ids);

    $this->db->get(); 
    $query2 =  $this->db->last_query();
    $query = $this->db->query($query1." UNION ".$query2);

    return $query->result();
}
1
Ameen Maheen

これは私が使用しているソリューションです:

$union_queries = array();
$tables = array('table1','table2'); //As much as you need
foreach($tables as $table){
    $this->db->select(" {$table}.row1, 
                        {$table}.row2,
                        {$table}.row3");
    $this->db->from($table);
    //I have additional join too (removed from this example)
    $this->db->where('row4',1);
    $union_queries[] = $this->db->get_compiled_select();
}
$union_query = join(' UNION ALL ',$union_queries); // I use UNION ALL
$union_query .= " ORDER BY row1 DESC LIMIT 0,10";
$query = $this->db->query($union_query);
1
Levan Abashidze

bwisnの答えはすべてより優れており、動作しますが、サブクエリを最初に実行するため、パフォーマンスは良くありません。 get_compiled_selectはクエリを実行しません。それは後で実行するためにコンパイルするだけなので、これを試してみてください

$this->db->select('title, content, date');
$this->db->where('condition',value);
$query1= get_compiled_select("table1",FALSE);
$this->db->reset_query();

$this->db->select('title, content, date');
$this->db->where('condition',value);
$query2= get_compiled_select("table2",FALSE);
$this->db->reset_query();

$query = $this->db->query("$query1 UNION $query2");
0
Dilpazir Ahmad