MySQL - 如果在其他表中出现超过x次,则选择行

时间:2017-11-15 13:49:14

标签: mysql sql join count

假设我有两个表,成员和订单与1:N关系:

Members         | Orders
UserID  Name    | OrderID   UserID  Name
111     Peter   | 777       111     Peter
222     Bart    | 888       333     Joe
333     Joe     | 999       111     Peter
444     Andrew  | 101       444     Andrew
                | 102       111     Peter
                | 103       333     Joe

我正在尝试从Members表中获取会员ID,以防会员在Orders表中有超过1个订单。

所以结果应该是......

Members
UserID  Name
111     Peter
333     Joe

...因为Peter和Joe在Orders表中至少有2个订单。

我试图通过以下方式获得结果:

SELECT
    s.UserID,
FROM Members s
    INNER JOIN Orders o
        ON s.UserID = o.UserID
WHERE
    s.UserID IN
    (
        SELECT UserID
        FROM Orders
        GROUP BY UserID
        HAVING COUNT(*) > 5
    )

但是,这给了我3次彼得,乔2次;所以我得到重复项而不是每个UserID一次。如何在没有重复的情况下获得结果?

5 个答案:

答案 0 :(得分:4)

我假设(并且希望)您没有存储两次用户名,因为当用户更改其名称时会导致数据质量问题。

假设表的结构如下:

CREATE TABLE
  Members
(
    UserID INT,
    Name VARCHAR(15)
);

INSERT INTO
  Members
VALUES
(111, 'Peter'),
(222, 'Bart'),
(333, 'Joe'),
(444, 'Andrew');

CREATE TABLE
  Orders
(
   OrderID INT,
   UserID INT
);

INSERT INTO
  Orders
VALUES
(777, 111),
(888, 333),
(999, 111),
(101, 444),
(102, 111),
(103, 333);

您可以使用GROUP BYHAVING条款,该条款会为所有用户UserID提供超过1(或您选择的数字)的订单。然后,将其加入Members表以获取名称。

SELECT
  Orders.UserID,
  Members.Name
FROM
  Orders
INNER JOIN
  Members
  ON Orders.UserID = Members.UserID
GROUP BY
  UserID,
  Members.Name
HAVING
  COUNT(OrderID) > 1;

SQLFiddle:http://sqlfiddle.com/#!9/1dadc4/2

但是,如果您已经存储了名称(并且没有更改),那么您可以跳过JOIN,如下所示:

SELECT
  UserID,
  Name
FROM
  Orders
GROUP BY
  UserID,
  Name
HAVING
  COUNT(OrderID) > 1

答案 1 :(得分:2)

这是你想要的吗?

SELECT
    s.UserID,
    s.Name
FROM 
    Members s
INNER JOIN 
    Orders o ON s.UserID = o.UserID
GROUP BY
    s.UserID
HAVING
    COUNT(*) > 5

答案 2 :(得分:0)

要删除重复项,请使用DISTINCT。

const WebSocket = require('ws');

const wss = new WebSocket.Server({ port: 8080 });

wss.on('message', function incoming(ws, message) {
  // Access to ws object
  console.log('received: %s', message);
});

答案 3 :(得分:0)

这里的答案,尽量避免使用DISTINCT

SELECT 
 UserID
 ,counts.count
FROM
 Members mem

JOIN (SELECT UserID,COUNT(*) as 'count' FROM Orders WHERE COUNT(*) > 1 GROUP BY UserID) counts
ON mem.UserID = counts.UserID

答案 4 :(得分:0)

您只需要具有count(OrderID) > 1的子查询,如下所示。

SELECT *
FROM members
WHERE UserID IN (
        SELECT UserId
        FROM orders
        GROUP BY userid
        HAVING count(OrderID) > 1
        );

<强>结果:

UserID  Name
--------------
111     Peter 
333     Joe  

DEMO