如何更正和重写此查询?

时间:2013-03-20 13:22:03

标签: mysql

SELECT * 
FROM users
WHERE id
IN ( 2024 ) 
AND id NOT IN (
    SELECT user_id
    FROM  `used` 
    WHERE DATE_SUB( DATE_ADD( CURDATE( ) , INTERVAL 7 DAY ) , INTERVAL 14 DAY ) <= created)
AND id NOT IN (
    SELECT user_id
    FROM coupon_used
    WHERE code =  'XXXXX')
AND id IN (
    SELECT user_id
    FROM accounts)

我在用户表中有id 2024,但这个id 2024在二手表中。因此,当我运行此查询时,它也显示我2024 id,应该过滤掉。我运行查询,我选择了特定用户,然后我希望这些用户过滤掉它们不应该在使用的表中。但上面的查询并没有给我想要的结果。欲望结果是我想通过以下条件选择用户:选择特定用户,并检查它们是否在使用的表中而不是在coupon_used表中,但它们应该在帐户表中。

3 个答案:

答案 0 :(得分:1)

首先,使用连接尝试这样的事情。这应该更容易阅读和(取决于MySQL的版本)更快

SELECT DISTINCT users.* 
FROM users
INNER JOIN accounts ON users.id = accounts.user_id
LEFT OUTER JOIN coupon_used ON users.id = coupon_used.user_id AND coupon_used.code = 'XXXXX'
LEFT OUTER JOIN `used` ON users.id = `used`.user_id AND DATE_SUB( DATE_ADD( CURDATE( ) , INTERVAL 7 DAY ) , INTERVAL 14 DAY ) <= `used`.created
WHERE id IN ( 2024 ) 
AND coupon_used.user_id IS NULL
AND `used`.user_id IS NULL

编辑 - 简化日期检查: -

SELECT DISTINCT users.* 
FROM users
INNER JOIN accounts ON users.id = accounts.user_id
LEFT OUTER JOIN coupon_used ON users.id = coupon_used.user_id AND coupon_used.code = 'XXXXX'
LEFT OUTER JOIN `used` ON users.id = `used`.user_id AND DATE_SUB( CURDATE( ) , INTERVAL 7 DAY ) <= `used`.created
WHERE id IN ( 2024 ) 
AND coupon_used.user_id IS NULL
AND `used`.user_id IS NULL

答案 1 :(得分:1)

我会使用左连接作为排除条件,并使用常规连接来包含:

SELECT users.*
FROM users
INNER JOIN accounts ON accounts.user_id = users.id
LEFT JOIN used ON used.user_id = users.id AND DATE_SUB(CURDATE(), INTERVAL 7 DAY) <= used.created)
LEFT JOIN coupon_used ON coupon_used.user_id = users.id AND coupon_used.code = 'XXXX'
WHERE id IN (2024) AND used.user_id IS NULL AND coupon_used.user_id IS NULL

我也编辑了日期操作; +7 -14将是-7:)

答案 2 :(得分:1)

我建议在帐户上使用JOIN,在其他两个表上使用LEFT OUTER JOIN。帐户上的JOIN表示它必须位于帐户表中。 coupon_used和used上的LEFT OUTER JOINS意味着它将返回一条记录,无论它们是否在该表中。过滤到c.user_id IS NULL表示该表中没有记录。

SELECT users.* 
FROM users
    JOIN accounts ON users.id = accounts.user_id
    LEFT OUTER JOIN coupon_used c ON users.id = c.user_id AND c.code = 'XXXXX'
    LEFT OUTER JOIN `used` u ON users.id = u.user_id AND DATE_SUB( DATE_ADD( CURDATE( ) , INTERVAL 7 DAY ) , INTERVAL 14 DAY ) <= u.created
WHERE id IN ( 2024 ) 
AND c.user_id IS NULL
AND u.user_id IS NULL