唯一约束,如何避免重复


Unique constraint, how to avoid duplicates

根据我以前的查询,我有一个表,看起来像这样:

|| *nid* || *language* ||
|| 8 || Chinese ||
|| 8 || Portuguese ||
|| 8 || German |

其中'nid'和'language'具有唯一的约束。

有了这个设置,我怎么能确保不会有任何重复,当我试图插入一个新的行?

我猜我应该试着做一个查询,如:

SELECT * FROM lang WHERE nid = $nid AND language = $lang

如果这个返回FALSE,那么我知道我现在可以插入我的数据了。

通过创建唯一键来强制惟一约束:

ALTER TABLE the_table
ADD UNIQUE INDEX nid_language_unique (nid, language);

此约束禁止具有相同id和语言的两行。

任何试图违反约束的查询都将失败。

如果您想忽略错误(并且仍然中止查询),您可以使用INSERT ignore和UPDATE ignore:

INSERT IGNORE INTO the_table (nid, language) VALUES (8, 'Chinese')
/* row not inserted and no error */

如果你已经在数据库中建立了一个唯一的约束,那么MySQL将不允许你插入第二行。该语句将引发异常。您可以在代码中捕获并忽略它。如果你对该行是否被添加不感兴趣,你可以在MySQL INSERT INTO命令中使用IGNORE键,该行要么被添加(如果不存在),要么命令将完成而没有错误。

SELECT nid, language FROM lang WHERE nid = $nid AND language = $lang

如果这个返回FALSE,那么我知道我现在可以插入我的数据了。

是的,但是你需要写:

$nid = mysql_real_escape_string($_POST['nid']);
$lang = mysql_real_escape_string($_POST['lang']);
$query = SELECT nid, language FROM lang WHERE nid = '$nid' AND language = '$lang'
// notice the quotes                                ^    ^                ^     ^

如果你忘记了这些,你的查询就会出错(并且有被sql注入的风险)。

如果你有一个唯一的约束,你可以直接插入数据,因为MySQL会为你做上面的测试。

您可以在代码中使用计数器(不是SQL,而是用于使用SQL的计数器,如PHP或其他)

你可以使用MySQL的max函数并添加一个(如max(nid)+1(但不要记得MySQL的max函数))

你可以使用一个10个字符的随机数(这样你就会有非常非常低的出错风险)

第一种方法和最后一种方法我用了很多次。

如果你想确保你不会有重复的,使用你上一篇文章中的解决方案。像UNIQUE约束这样的东西会防止您插入两次相同的nid或语言(因此,如果您不处理它,您的程序将崩溃)。