我正在学习SQL并使用Mysql来计算查询。关于主键的主题,我读了
无论哪一列被声明为主键,它都不能 null 。
所以,我制作了一个简单的employee
表,其中id
和name
字段PRIMARY KEY
为id
;
并提出以下问题,
INSERT INTO employee (id, name) VALUES (1, 'John');
INSERT INTO employee (id, name) VALUES (2, 'Frank');
现在,为了测试主键列不是 Null 属性,我输入了以下查询。
INSERT INTO employee(name) VALUES('Joe');
原来没有显示错误,查询成功运行
从整个表中选择记录后,我看到了
id |name
0 | Joe
1 | John
2 | Frank
我希望看到类似
的错误专栏' id'不能为NULL
但正如您所看到的,Joe的主键自动设置为0。 我尝试再次插入而没有给出id
现在我收到了消息,
重复输入' 0'关键' PRIMARY'
那么这里发生了什么?并且主要密钥不是从1
开始的吗?
答案 0 :(得分:2)
MySQL(5.7之前)对主键使用隐式默认值0,请参阅documentation:
如果列不能将NULL作为值,则MySQL定义没有显式DEFAULT子句的列。例外:如果列被定义为PRIMARY KEY的一部分但未显式为NOT NULL ,则MySQL会将其创建为NOT NULL列(因为PRIMARY KEY列必须为NOT NULL)。 在MySQL 5.7.3之前,还使用隐式默认值为该列分配了DEFAULT子句。为防止这种情况,请在任何PRIMARY KEY列的定义中包含显式NOT NULL。
如果将null
插入此类列中,则会采用隐式值,除非您设置了严格模式:
对于没有显式DEFAULT子句[...]
的NOT NULL列的数据输入
如果启用了严格的SQL模式,则事务表会发生错误,并且会回滚该语句。对于非事务性表,会发生错误,但如果多行语句的第二行或后续行发生这种情况,则会插入前面的行。
如果未启用严格模式,MySQL会将列设置为列数据类型的隐式默认值。
数值类型的隐式默认值为0.因此,每次使用null
(或根本不使用该列)时,MySQL都使用0
。这是第一次,但不是第二次。
答案 1 :(得分:1)
您已在id
字段中设置了AUTO_INCREMENT
属性。这是一个很好的小功能,可确保价值始终是唯一的,因此您不必担心它是null
,并担心重要的事情。但是如果你试试这个,肯定会引发错误;
INSERT INTO `employee` (`id`, `name`) VALUES (null, `Joe`);
编辑啊,我没看到你发布的错误。这里发生了什么;你确实不设置AUTO_INCREMENT
属性(虽然你应该有;))。现在,id
字段是整数字段。如果你没有给出任何值,mysql会尝试通过给它最可能的值来保存你的屁股,或者最接近没有任何值的值,0
。第一次一切顺利,第二次看到该值已经存在,并且失败了。