INSERT除非存在于其他表中

时间:2015-07-22 14:20:48

标签: php mysql

我的wesite上有users表,我想编写将email列的函数并将其插入不同的表mailing_list,但仅当电子邮件不是那里不存在。

对于这个问题,您可以假设每个表都有以下列:IDusernameemail

这是我目前的代码:

$get_mails = $db->query("SELECT `username`,`email`,`email_approved`,`ver` FROM `users` WHERE ver='yes' && email_approved='1'");
while ($mails = $get_mails->fetch_assoc())  {
    if ($db->query("SELECT `email` FROM `mailing_list` WHERE email='".$mails['email']."'")->num_rows == 0)  {
        $db->query("INSERT INTO `mailing_list` VALUES('','".$mails['email']."','".$mails['username']."')");         
    }
}

正如你所看到的那样效率不高。有一种方法可以在INSERT查询本身中执行此操作吗?

谢谢。

3 个答案:

答案 0 :(得分:2)

一种(有点脏)解决方案是在email中的mailing list字段上添加唯一索引,这样可以防止双重输入,因此您不必先进行选择查询。

编辑,示例:

$db->query
(
    "INSERT IGNORE INTO `mailing_list` 
    SELECT '',email,username FROM `users`
    WHERE ver = 'yes' AND email_approved = '1'"
);

答案 1 :(得分:2)

我建议使用INSERT ... SELECT方法,它允许您使用连接进行过滤,并使用单个查询执行所有插入,而不是迭代查询。

这可能是这样的:

INSERT INTO mailing_list (email, username)
SELECT u.email, u.username
FROM users AS u
LEFT JOIN mailing_list AS ml
  ON u.email = ml.email
WHERE
  /* this filters to only those records that don't exist in mailing_list */
  ml.email IS NULL
  /* these are conditions from your initial query as shown */
  AND u.ver = 'yes'
  AND u.email_approved = '1'

要优化查询,您需要u.emailu.veru.email_approvedml.email上的索引。这也假设你在ml.id上有一个自动增量索引,这样当插入没有指定该字段的值时,它就会顺序得到下一个数字。

您未来编码的提示 - 当您发现自己想要在循环中进行查询时,您应该更仔细地查看代码,因为通常有更好的方法来简化数据访问。

答案 2 :(得分:0)

Try this query: First query will stay as it is and this query is for next 2 queries
INSERT INTO `mailing_list` (email) select ".$mails['email']." from mailing_list where (select count(.$mails['email'].) from test1 where  name1 = '.$mails['email'].') = 0 limit 1;

示例查询:

Insert into mailing_list (email) select "z.y@z.com" from mailing_list where (select count(email) from mailing_list where email='z.y@z.com' and ) = 0 limit 1;

这会将电子邮件字符串作为输出

select "z.y@z.com" from mailing_list where 

这将验证表格中存在电子邮件的位置(如果计数为0,将插入新电子邮件,如果不插入电子邮件

select count(email) from mailing_list where email='z.y@z.com') = 0

这是为了限制不匹配的电子邮件

limit 1