我有一个表格,其中包含有关注册用户的信息。类似的东西:
umeta_id | user_id | meta_key | meta_value
---------|---------|-------------|-------------
1 | 1 | nickname | value
2 | 1 | first_name | value
3 | 1 | custom_key | value
4 | 2 | nickname | value
5 | 2 | first_name | value
6 | 3 | nickname | value
7 | 3 | first_name | value
8 | 3 | custom_key | value
注册有两种形式,因此与注册用户对应的行数会因注册时使用的形式而异。
例如,如果用户使用表单A进行注册,则会有custom_key
与该用户关联的行。如果用户使用表单B,则没有custom_key
行。将行与user_id
1
和2
进行比较。 1
使用表单A注册,2
使用表单B注册。
我可以通过custom_key
(使用表单A)获取用户,但是如何获取使用表单B的用户,即没有custom_key
行的用户?
这个SELECT * FROM rfs_usermeta WHERE meta_key = 'custom_key'
返回使用表单A的行/用户。我需要做相反的事情。
在JS中,我把它写成:
var users = {};
// loop usermeta rows
for (var row in rfs_usermeta) {
// group rows with same user_id
users[row.user_id][row.meta_key] = value;
}
var result = [];
// loop grouped rows
for (var user in users) {
// assume users don't have custom_key row
var rowExists = false;
// loop user keys
for (var key in user) {
// check if custom_key exists
if (key == "custom_key") {
// mark current user
rowExists = true;
break;
}
}
// ignore marked users
if (!rowExists) {
result.push(user);
}
}
答案 0 :(得分:2)
SELECT *
FROM rfs_usermeta
WHERE user_id NOT IN( SELECT user_id FROM rfs_usermeta WHERE meta_key='custom_key')
如果可以使用数据库进行过滤,则永远不想使用PHP进行过滤。您的数据库旨在收集/订购/过滤数据,并且可以快速执行 super ,其中PHP循环要慢得多。
答案 1 :(得分:1)
SQL在基于集合的方法中运行最佳:为所有用户获取一组数据。以及具有自定义键的用户的一组数据。然后基本上减去这两个:所有用户少用自定义密钥=用户没有自定义密钥。
相关子查询,但不存在。
只需获得一组具有自定义密钥的用户即可。然后是一组所有记录,除了具有自定义键的集合中的那些记录。
SELECT *
FROM rfs_usermeta A
WHERE NOT EXISTS (SELECT *
FROM rfs_usermeta B
WHERE A.umeta_id = B.umeta_id
and B.meta_key = 'custom_key')
左连接也可以使用类似的前提
SELECT *
FROM rfs_usermeta A
LEFT JOIN rfs_usermeta B
on A.umeta_id = B.umeta_id
and B.meta_ket = 'custom_key'
WHERE B.user_ID is null
答案 2 :(得分:0)
SELECT * FROM rfs_usermeta r
HAVING (SELECT COUNT(*) FROM rfs_usermeta r2 where r2.user_id = r.user_id
meta_key = 'custom_key') = 0