2017-07-17 16 views
-1

I do not explain the logic of the query、これは簡単ではないので、私が詳細に説明するなら、誰もその質問の本質を読んで掘り下げたいとは思わないでしょう。MySQL:subquerysまたは共用体ですか?

質問が2つあります。彼らは仕事をうまくやっています。結果:同一。手動モードでチェックされ、紙の鉛筆(およびデータベース)に表示されます。

サーバーの負荷が少ないクエリはどれですか?それとも、実際の(プロダクション)サーバーで作業した後で、それはちょっと見付かるでしょうか?


操作UNION非常に負荷がかかりますか?あなたが別の一連のレコード数の合計を探しているように見えますWhat should I look for in the explanations of the querys?


1のq whith + + +

select (select count(comid) from coms join posts on pid=pid_coms where uid_posts=8888 and uid_coms=8888) 

+ 
(select count(comid) from frends join posts on sl_frend=uid_posts join coms on pid=pid_coms 
where uid_coms=8888 and m_frend=8888 and ((postacc=1 and postcomacc=2) or (postacc=2 and postcomacc=2) or (postacc=2 and postcomacc=1))) 

+ 
(select count(comid) from frends join posts on m_frend=uid_posts join coms on pid=pid_coms 
where uid_coms=8888 and sl_frend=8888 and ((postacc=1 and postcomacc=2) or (postacc=2 and postcomacc=2) or (postacc=2 and postcomacc=1))) 

+ 
(select count(comid) from coms join posts on pid_coms=pid where uid_posts != 8888 and uid_coms=8888 and postacc=1 and postcomacc=1) CountMyComms; 

EXPLAIN 
+----+-------------+--------+--------+-----------------------+----------+---------+---------------------+------+----------------+ 
| id | select_type | table | type | possible_keys   | key  | key_len | ref     | rows | Extra   | 
+----+-------------+--------+--------+-----------------------+----------+---------+---------------------+------+----------------+ 
| 1 | PRIMARY  | NULL | NULL | NULL     | NULL  | NULL | NULL    | NULL | No tables used | 
| 5 | SUBQUERY | coms | ref | uid_coms,pid_coms  | uid_coms | 4  | const    | 7 |    | 
| 5 | SUBQUERY | posts | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where | 
| 4 | SUBQUERY | frends | ref | m_frend,sl_frend  | sl_frend | 4  | const    | 1 |    | 
| 4 | SUBQUERY | coms | ref | uid_coms,pid_coms  | uid_coms | 4  | const    | 7 |    | 
| 4 | SUBQUERY | posts | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where | 
| 3 | SUBQUERY | coms | ref | uid_coms,pid_coms  | uid_coms | 4  | const    | 7 |    | 
| 3 | SUBQUERY | posts | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where | 
| 3 | SUBQUERY | frends | ref | m_frend,sl_frend  | sl_frend | 4  | mbs.posts.uid_posts | 1 | Using where | 
| 2 | SUBQUERY | coms | ref | uid_coms,pid_coms  | uid_coms | 4  | const    | 7 |    | 
| 2 | SUBQUERY | posts | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where | 
+----+-------------+--------+--------+-----------------------+----------+---------+---------------------+------+----------------+ 
11 rows in set (0.00 sec) 

2組合

select count(comid) from (select comid from coms join posts on pid=pid_coms where uid_posts=8888 and uid_coms=8888 

union 
select comid from frends join posts on sl_frend=uid_posts join coms on pid=pid_coms 
where uid_coms=8888 and m_frend=8888 and ((postacc=1 and postcomacc=2) or (postacc=2 and postcomacc=2) or (postacc=2 and postcomacc=1)) 

union 
select comid from frends join posts on m_frend=uid_posts join coms on pid=pid_coms 
where uid_coms=8888 and sl_frend=8888 and ((postacc=1 and postcomacc=2) or (postacc=2 and postcomacc=2) or (postacc=2 and postcomacc=1)) 

union 
select comid from coms join posts on pid_coms=pid 
where uid_posts != 8888 and uid_coms=8888 and postacc=1 and postcomacc=1) a; 

EXPLAIN 
+----+--------------+----------------+--------+-----------------------+----------+---------+---------------------+------+------------------------------+ 
| id | select_type | table   | type | possible_keys   | key  | key_len | ref     | rows | Extra      | 
+----+--------------+----------------+--------+-----------------------+----------+---------+---------------------+------+------------------------------+ 
| 1 | PRIMARY  | NULL   | NULL | NULL     | NULL  | NULL | NULL    | NULL | Select tables optimized away | 
| 2 | DERIVED  | coms   | ref | uid_coms,pid_coms  | uid_coms | 4  |      | 7 |        | 
| 2 | DERIVED  | posts   | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where     | 
| 3 | UNION  | coms   | ref | uid_coms,pid_coms  | uid_coms | 4  |      | 7 |        | 
| 3 | UNION  | posts   | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where     | 
| 3 | UNION  | frends   | ref | m_frend,sl_frend  | sl_frend | 4  | mbs.posts.uid_posts | 1 | Using where     | 
| 4 | UNION  | frends   | ref | m_frend,sl_frend  | sl_frend | 4  |      | 1 |        | 
| 4 | UNION  | coms   | ref | uid_coms,pid_coms  | uid_coms | 4  |      | 7 |        | 
| 4 | UNION  | posts   | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where     | 
| 5 | UNION  | coms   | ref | uid_coms,pid_coms  | uid_coms | 4  |      | 7 |        | 
| 5 | UNION  | posts   | eq_ref | PRIMARY,pid,uid_posts | PRIMARY | 4  | mbs.coms.pid_coms | 1 | Using where     | 
| NULL | UNION RESULT | <union2,3,4,5> | ALL | NULL     | NULL  | NULL | NULL    | NULL |        | 
+----+--------------+----------------+--------+-----------------------+----------+---------+---------------------+------+------------------------------+ 
12 rows in set (0.00 sec) 
+0

あなたは 'COUNT(comid)'を使用する必要がありますか?または 'COUNT(*)'を使用できますか? ( 'COUNT(*)'は少し速いです。)2回目のクエリでは、 'UNION'の各部分が返す' comid'値のセットがありますか?そうであれば、 –

+0

''ヌル ''いいえ、いいえ、私はCOUNT(*)を使用します。 –

答えて

1

whith Qテーブルのクエリ。

最初の選択肢...各クエリの結果をカウントし、それらを追加すると高速になります。どうして?それはするべき仕事が少ない。あなたの2番目の選択肢は、comidの値のセットを争い、それらを数えなければなりません。それには時間がかかる。

可能であればCOUNT(*)を使用してください。それは安価です。可能であればUNIONの代わりにUNION ALLを使用してください。 UNIONは重複を削除し、UNION ALLは削除しません。重複を削除するには時間がかかります。

いずれの代替方法のパフォーマンスは、各サブクエリのインデックスの適切な選択に依存します。

+0

'duolicates'は不可能です、インデックスは存在します。この実行時間(whith any)は' UNION ALL'を使用します。クエリのSは0.08秒以下です。約70,000〜100,000レコードでテストされていますが、すべて正常です。今後、本番サーバーを監視する必要があります。 –

関連する問題