如何有效地检索同一表中的相交值?

时间:2019-01-01 04:02:30

标签: mysql node.js

假设我有下表“ some_table”,看起来像这样

email | friend_email |
----------------------
s1    | f1           |
----------------------
s2    | f1           |
----------------------
s1    | f2           |
----------------------
s2    | f2           |
----------------------
s3    | f2           |
----------------------
s1    | f3           |
----------------------
s2    | f3           |
----------------------
s4    | f3           |

然后我想在f1,f2和f3之间的“电子邮件”下找到不同的通用值。 返回的结果只能是s1和s2。

使用的SQL语句如下所示,

SELECT DISTINCT email FROM some_table WHERE friend_email IN ('f1') AND email in (SELECT DISTINCT email FROM some_table WHERE friend_email IN ('f2')) AND email in (SELECT DISTINCT email FROM some_table WHERE friend_email IN ('f3'));

这个问题是当我有更多的Friend_emails要添加时,它将变得非常冗长。

在我的node.js代码中,我想使用'?' (我认为它们被称为常量?),但是我没有成功。下面是代码示例,

var getCommonFriends = "SELECT DISTINCT email FROM some_table WHERE friend_email = '?'";
var getCommonFriendsAppend = " AND email in (SELECT DISTINCT email FROM some_table WHERE friend_email = '?')";

var friends = ["f1", "f2", "f3"];

var combinedSqlStatement = getCommonFriends;
var totalFriends = friends.length;
for(var i = 0; i < totalFriends; i++){
    combinedSqlStatement = combinedSqlStatement + getCommonFriendsAppend;
}

我的问题是我该如何执行上面的操作并使用常量aka'?'的sql语句?

1 个答案:

答案 0 :(得分:2)

我认为您可以在此处执行简单的汇总查询:

SELECT email
FROM some_table
WHERE friend_email IN ('f1', 'f2', 'f3')
GROUP BY email
HAVING COUNT(DISTINCT friend_email) = 3;

此选项按电子邮件项目聚合,然后断言该项目中存在/关联了一组特定的朋友。该解决方案可以很好地扩展,因为要扩展到更多的朋友,您只需向IN子句添加另一个朋友,并在查询结束时更改不重复计数声明即可。

Demo

这是查询的一个版本,在Node JS中可能更友好:

SELECT email
FROM some_table
WHERE friend_email IN
(
    SELECT ? FROM dual UNION ALL
    SELECT ? FROM dual UNION ALL
    SELECT ? FROM dual
)
GROUP BY email
HAVING COUNT(DISTINCT friend_email) = 3;

然后,将文字值'f1''f2''f3'绑定到上述查询。

Demo