我有一些简化的数据:

mysql> SELECT * FROM tbl_task;
+----+----------+
| id | data     |
+----+----------+
|  1 | data 1   |
|  2 | data 2   |
|  3 | data 3   |
|  4 | data 4   |
|  5 | data 55  |
|  6 | data 166 |
+----+----------+

mysql> SELECT * FROM tbl_parameter;
+----+---------+----------+
| id | task_id | name     |
+----+---------+----------+
|  1 |       1 | hardware |
|  2 |       1 | hardware |
|  3 |       1 | hardware |
|  4 |       2 | hardware |
|  5 |       2 | hardware |
|  6 |       3 | hardware |
|  7 |       3 | hardware |
|  8 |       3 | hardware |
|  9 |       4 | hardware |
| 10 |       5 | hardware |
| 11 |       5 | hardware |
| 12 |       5 | hardware |
| 13 |       6 | hardware |
| 14 |       6 | hardware |
+----+---------+----------+

mysql> SELECT * FROM tbl_parameter_value;
+----+--------------+---------+
| id | parameter_id | value   |
+----+--------------+---------+
|  1 |            1 | modem   |
|  2 |            2 | printer |
|  3 |            3 | 220     |
|  4 |            4 | 24      |
|  5 |            5 | modem   |
|  6 |            6 | printer |
|  7 |            7 | 220     |
|  8 |            8 | gps     |
|  9 |            9 | 24      |
| 10 |           10 | printer |
| 11 |           11 | modem   |
| 12 |           12 | 220     |
| 13 |           13 | 24      |
| 14 |           14 | modem   |
+----+--------------+---------+


因此,任务有多个参数,每个参数都有一个值。似乎没有意义,但这只是简化的数据。

我使用两个联接来获取value数据:

mysql> SELECT tbl_task.id, tbl_parameter_value.value
    -> FROM tbl_task
    -> LEFT JOIN tbl_parameter ON tbl_task.id = tbl_parameter.task_id
    -> LEFT JOIN tbl_parameter_value ON tbl_parameter.id = tbl_parameter_value.parameter_id;
+----+---------+
| id | value   |
+----+---------+
|  1 | modem   |
|  1 | printer |
|  1 | 220     |
|  2 | 24      |
|  2 | modem   |
|  3 | printer |
|  3 | 220     |
|  3 | gps     |
|  4 | 24      |
|  5 | printer |
|  5 | modem   |
|  5 | 220     |
|  6 | 24      |
|  6 | modem   |
+----+---------+


如您所见,task.id列中有一些重复项。我需要过滤此查询以同时仅返回参数值modem AND printer的任务。

以下查询显然没有任何意义:

SELECT tbl_task.id, tbl_parameter_value.value
FROM tbl_task
LEFT JOIN tbl_parameter ON tbl_task.id = tbl_parameter.task_id
LEFT JOIN tbl_parameter_value ON tbl_parameter.id = tbl_parameter_value.parameter_id
WHERE value LIKE '%modem%' AND value LIKE '%printer%'


我也尝试过:

SELECT tbl_task.id, tbl_parameter_value.value
FROM tbl_task
LEFT JOIN tbl_parameter ON tbl_task.id = tbl_parameter.task_id
LEFT JOIN tbl_parameter_value ON tbl_parameter.id = tbl_parameter_value.parameter_id AND tbl_parameter_value.value LIKE '%modem%' OR tbl_parameter_value.value LIKE '%printer%'


它给出了错误的结果以太。

如何同时使用参数值调制解调器和打印机过滤仅不同的任务?
根据这些数据,我需要获取的是:

+----+
| id |
+----+
|  1 |
|  5 |
+----+

最佳答案

由于您需要查找参数值modemprinter的任务,因此有必要在查询中将表tbl_parametertbl_parameter_value联接两次(使用表别名):

SELECT t.id
FROM tbl_task t
INNER JOIN tbl_parameter tp1 ON t.id = tp1.task_id
INNER JOIN tbl_parameter tp2 ON t.id = tp2.task_id
INNER JOIN tbl_parameter_value tpv1 ON tp1.id = tpv1.parameter_id
INNER JOIN tbl_parameter_value tpv2 ON tp2.id = tpv2.parameter_id
WHERE tpv1.value LIKE '%modem%' AND tpv2.value LIKE '%printer%'


如果要测试参数值是否完全等于modemprinter,则可以将WHERE子句替换为:

WHERE tpv1.value = 'modem' AND tpv2.value = 'printer'


注意:如果使用LEFT JOIN而不是INNER JOIN,查询将始终返回id中的所有tbl_task值。这显然不是预期的结果。

阅读documentation about the JOIN syntax了解更多信息。

关于mysql - 从两个左联接中过滤数据,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/43340992/

10-14 02:14
查看更多