我正在使用存储过程,显然下面不是我的确切代码,而是一个高度修剪的版本来实现这个想法。请记住,我实际上已在此临时表上进行了大量过滤,因此向CREATE TABLE
查询添加任何内容都会比任何事情更麻烦。
BEGIN
CREATE TEMPORARY TABLE IF NOT EXISTS filtered_results AS (SELECT * FROM users);
# Numerous filters removing stuff from the table.
END
出于这个问题的目的,我们可以说表结构非常简单,如下所示:
user_id INT(11) AUTO_INCREMENT PRIMARY
name VARCHAR(30) NOT NULL
现在让我们说我有一个具有以下结构的问题表:
question_id INT(11) AUTO_INCREMENT PRIMARY
user_id INT(11)
text VARCHAR(40)
现在假设我想迭代表并检查一些其他表来过滤没有至少4个问题的用户。所以像这样:
for each row in filtered_results
if count(question_id) < 4 where user_id = row.user_id in questions
delete row
end if
end loop
答案 0 :(得分:1)
经过一些讨论和你的最后评论后,我想我提出了一个比运行游标更优雅的解决方案(正如我之前在评论中提到的那样)。
您需要根据LEFT JOIN
的{{1}}和to_be_deleted_table
表格对结果中运行删除命令。我考虑到您的questions
上有user_id。
考虑这个样本:
to_be_deleted_table
此示例包含您所说的内容,拥有4个(或更多问题)的用户,少于4个问题的用户以及完全的用户根本没有问题。
删除用户不至少有4个问题的查询将是:
create table filtered_results (
user_id integer,
name varchar(10)
);
insert into filtered_results values
(1, 'Bob'), (2, 'Sally'), (3, 'Cheer'), (4, 'Sid'), (5, 'Simon'),
(6, 'Lua'), (7, 'Liv'), (8, 'Taylor'), (9, 'Jay'), (10, 'Mike');
create table questions (
question_id integer,
user_id integer
);
insert into questions values
(1, 1), (2, 1), (3, 1), (4, 1), (5, 1),
(6, 2), (7, 2),
(8, 3), (9, 3), (10, 3), (11, 3),
(12, 4), (13, 4), (14, 4), (15, 4),
(16, 5), (17, 5), (18, 5), (19, 5),
(20, 6), (21, 6), (22, 6), (23, 6),
(24, 7), (24, 7), (24, 7), (24, 7);
你一定想知道为什么我有两个子选择,这是因为你需要欺骗编译器,这样就可以从你正在进行select的同一个表中删除行,在本例中是delete
from filtered_results
where user_id in
(select user_id
from (select f.user_id
from filtered_results f
LEFT JOIN questions q ON (f.user_id = q.user_id)
group by f.user_id
having count(*) < 4) a
);
。
如果要根据过滤表中的user_id从另一个表中删除,请执行以下操作:
filtered_results
请记住,如果是这种情况,您不需要创建delete
from users
where user_id in
(select f.user_id
from filtered_results f
LEFT JOIN questions q ON (f.user_id = q.user_id)
group by f.user_id
having count(*) < 4
);
,只需使用您在我展示的第一个案例中将其创建为子查询的查询。
希望它有所帮助。
如果您希望看到它正常工作,请查看此SQLFiddle