用LeftJoin不等于搜索

时间:2017-03-16 18:41:07

标签: mysql sql

我有一个查询

Select 
    m.name 

from machines m 
    innerJoin config c ON m.cod = c.cod

--> where ( c.category = 'BIOS' and c.val = 'System' )  
--> and   ( c.category = 'Users' and c.val = 'Jonas' )  

group by c.cod

* MACHINES ---------------- +
| key    | name    | cod    |
* ------ + ------- + ------ +
| 1      | M1      | 23     |
| 2      | M2      | 26     |
| 3      | M3      | 27     |
+ ------ + ------- + ------ +

* CONFIG --------------------------- +
| key    | category | cod   | val    |
+ ------ + -------- + ----- + ------ +
| 1      | BIOS     | 23    | System |
| 2      | Users    | 23    | Jonas  |
| 3      | Users    | 23    | Maria  |
| 4      | BIOS     | 26    | System |
| 5      | Users    | 26    | Jonas  |
| 6      | BIOS     | 27    | System |
| 6      | Users    | 27    | Ana    |
+ ------ + -------- + ----- + ------ +

我得到了

* RESULT -- +
| name      |
+ --------- +
| M1        |
| M2        |
+ --------- +

非常适合'平等'搜索,但我不知道我是如何进行'不等于'搜索此查询。

我试过了:

Select 
    m.name 

from machines m 
    innerJoin config c ON m.cod = c.cod

--> where ( c.category = 'BIOS' and c.val <> 'System' )  
--> or    ( c.category = 'Users' and c.val <> 'Jonas' )  

group by c.cod

但仍然获得机器'M1',值为'Maria'的字段与过滤器匹配

我需要使用此过滤器结果:

* RESULT -- +
| name      |
+ --------- +
| M3        |
+ --------- +

我该怎么办?

5 个答案:

答案 0 :(得分:2)

试试这个:

SELECT name FROM machines 
WHERE name NOT IN (
SELECT m.name FROM machines m    INNER JOIN config c ON m.cod = c.cod WHERE ( c.category = 'BIOS' and c.val = 'System' )  AND ( c.category = 'Users' and c.val = 'Jonas' ) GROUP BY c.cod)

答案 1 :(得分:1)

Select 
    m.name 

from machines m 
    innerJoin config c ON m.cod = c.cod

where NOT (
( m.category = 'BIOS' and m.val = 'System' )  
 and ( m.category = 'Users' and m.val = 'Jonas' )
) 

group by c.cod

答案 2 :(得分:1)

您发布的查询中一再出现错误:categoryval来自表格c,而不是m

然后,在我看来,你想要的是丢弃那些引用你的病情存在其他记录的机器的记录。不幸的是,仅凭记录条件无法做到这一点,所以否定条件是没有用的。你必须做这样的事情:

SELECT DISTINCT name 
  FROM machines 
 WHERE name NOT IN (
     SELECT m.name       
       FROM machines m 
       INNER JOIN config c USING (cod)
      WHERE ( c.category = 'BIOS' AND c.val = 'System' )  
        AND ( c.category = 'Users' AND c.val = 'Jonas' )
 )

答案 3 :(得分:0)

尝试以下脚本:

    SELECT M.Name FROM Machines AS M LEFT JOIN CONFIG AS C ON M.Cod=C.Cod 
    WHERE  NOT ( 
    (M.Category ='BIOS' AND M.Val='System') AND
    (M.Category ='Users' AND M.Val='Jonas') 
    )

NOT关键字是您查询的简便解决方案。我也做了左连接而不是内部,如果不需要你可以忽略它。

答案 4 :(得分:0)

Working SQL FIDDLE

由于您需要配对值才能为系统提供2条记录,因此我将其用于相等的

这确实假设类别/ cod / val在配置中是唯一的。

SELECT m.name
FROM machines m
INNER JOIN config c
  on c.cod = m.cod
WHERE (( c.category = 'BIOS' and c.val = 'System' )  
   OR ( c.category = 'Users' and c.val = 'Jonas' ))
GROUP BY m.name
having count(*) =2 ;

这对于不等于...注意如果你有更多的“OR”标记,那么2只会改变

SELECT m.name
FROM machines m
INNER JOIN config c
  on c.cod = m.cod
WHERE (( c.category = 'BIOS' and c.val = 'System' )  
   OR ( c.category = 'Users' and c.val = 'Jonas' ))
GROUP BY m.name
having count(*) <>2 ;