SQL 列出所有人购买的商品
SQL list items bought by everyone
关于如何在 SQL 中写这个有什么想法吗?
List all the customers who bought products bought by every other
架构是:
Customer
(cId, cName)
Buys
(tId, cId, pId)
Product
(pId, pName)
我一直在尝试 select 所有不同的项目并使用它对 table 购买进行分组,但没有成功。
-- Customers who bought products bought by every other customer
SELECT DISTINCT cId,cName
FROM Customer c1
,Buys b1
WHERE c1.cId = b1.cId
AND pId IN
-- Products bought by every other customer
(SELECT pId
FROM (SELECT pId,COUNT(1) count_p
FROM (SELECT DISTINCT
cId,pId
FROM Buys)
GROUP BY pId) t1
,(SELECT COUNT(1) count_c
FROM Customer) t2
WHERE t1.count_p = t2.count_c)
试试上面的查询,看看它是否有效。我没有机会测试这个。
试试这个,在随机数据上测试,效果很好。在大量数据上可能会很慢..
SELECT cid, NAME
FROM (SELECT c.cid, c.name, cc.cnt, COUNT(b.pid) cpid
FROM customer c, buys b, product p, (SELECT COUNT(*) cnt FROM customer) cc
WHERE c.cid = b.cid
AND b.pid = p.pid
GROUP BY c.cid, c.name, cc.cnt)
WHERE cpid = cnt
您想要一份客户列表,这些客户只购买了所有客户购买的产品。所以我认为您应该在子查询中将所有产品标记为 SoldToAll 或不是。然后,您必须确定您的客户是否购买了至少一种标记为 SoldToAll = 1 的产品和标记为 SoldToAll = 0 的产品中的 none。
-- Step 1. Flag products as SoldToAll
SELECT
pid
,CASE COUNT(*) = (SELECT COUNT(*) FROM Customer) THEN 1 ELSE 0 END AS SoldToAll
FROM
(SELECT cid,pid
FROM buys
GROUP BY cid,pid
) CustProd
GROUP BY
pid
-- Step 2. Use the above to get list
;WITH Prod AS
(SELECT
pid
,CASE COUNT(*) = (SELECT COUNT(*) FROM Customer) THEN 1 ELSE 0 END AS SoldToAll
FROM
(SELECT cid,pid
FROM buys
GROUP BY cid,pid
) CustProd
GROUP BY
pid)
SELECT
DISTINCT Buys.cid
FROM
Buys
WHERE
pid IN (SELECT pid FROM Prod WHERE SoldToAll = 1)
EXCEPT
SELECT
DISTINCT Buys.cid
FROM
Buys
WHERE
pid IN (SELECT pid FROM Prod WHERE SoldToAll = 0)
关于如何在 SQL 中写这个有什么想法吗?
List all the customers who bought products bought by every other
架构是:
Customer
(cId, cName)Buys
(tId, cId, pId)Product
(pId, pName)
我一直在尝试 select 所有不同的项目并使用它对 table 购买进行分组,但没有成功。
-- Customers who bought products bought by every other customer
SELECT DISTINCT cId,cName
FROM Customer c1
,Buys b1
WHERE c1.cId = b1.cId
AND pId IN
-- Products bought by every other customer
(SELECT pId
FROM (SELECT pId,COUNT(1) count_p
FROM (SELECT DISTINCT
cId,pId
FROM Buys)
GROUP BY pId) t1
,(SELECT COUNT(1) count_c
FROM Customer) t2
WHERE t1.count_p = t2.count_c)
试试上面的查询,看看它是否有效。我没有机会测试这个。
试试这个,在随机数据上测试,效果很好。在大量数据上可能会很慢..
SELECT cid, NAME
FROM (SELECT c.cid, c.name, cc.cnt, COUNT(b.pid) cpid
FROM customer c, buys b, product p, (SELECT COUNT(*) cnt FROM customer) cc
WHERE c.cid = b.cid
AND b.pid = p.pid
GROUP BY c.cid, c.name, cc.cnt)
WHERE cpid = cnt
您想要一份客户列表,这些客户只购买了所有客户购买的产品。所以我认为您应该在子查询中将所有产品标记为 SoldToAll 或不是。然后,您必须确定您的客户是否购买了至少一种标记为 SoldToAll = 1 的产品和标记为 SoldToAll = 0 的产品中的 none。
-- Step 1. Flag products as SoldToAll
SELECT
pid
,CASE COUNT(*) = (SELECT COUNT(*) FROM Customer) THEN 1 ELSE 0 END AS SoldToAll
FROM
(SELECT cid,pid
FROM buys
GROUP BY cid,pid
) CustProd
GROUP BY
pid
-- Step 2. Use the above to get list
;WITH Prod AS
(SELECT
pid
,CASE COUNT(*) = (SELECT COUNT(*) FROM Customer) THEN 1 ELSE 0 END AS SoldToAll
FROM
(SELECT cid,pid
FROM buys
GROUP BY cid,pid
) CustProd
GROUP BY
pid)
SELECT
DISTINCT Buys.cid
FROM
Buys
WHERE
pid IN (SELECT pid FROM Prod WHERE SoldToAll = 1)
EXCEPT
SELECT
DISTINCT Buys.cid
FROM
Buys
WHERE
pid IN (SELECT pid FROM Prod WHERE SoldToAll = 0)