23

我想限制 SQL 表中的列值。例如,列值只能是“car”或“bike”或“van”。我的问题是如何在 SQL 中实现这一点,在 DB 端这样做是个好主意,还是应该让应用程序限制输入。

我还打算在将来添加或删除更多值,例如“卡车”。

我使用的数据库类型是 SQLite 和 MySQL。

4

5 回答 5

36

添加一个包含这些交通工具的新表,并使您的列成为该表的外键。将来可以将新的交通工具添加到表中,并且您的列定义保持不变。

有了这种结构,我肯定会选择在数据库级别而不是应用程序级别来规范它。

于 2011-06-16T04:36:23.717 回答
26

对于 MySQL,您可以使用 ENUM 数据类型。

column_name ENUM('small', 'medium', 'large')

请参阅MySQL 参考:ENUM 类型

除此之外,我发现在数据库端应用端进行限制总是更好。一个枚举加上一个选择框,你就被覆盖了。

于 2011-06-16T04:35:11.787 回答
9

是的,建议添加检查约束。检查约束用于确保数据库中数据的有效性并提供数据完整性。如果在数据库级别使用它们,使用数据库的应用程序将无法添加无效数据或修改有效数据,因此数据变为无效,即使应用程序本身接受无效数据也是如此。

在 SQLite 中:

create table MyTable
(
    name string check(name = "car" or name = "bike" or name = "van")
);

在 MySQL 中:

create table MyTable
(
    name ENUM('car', 'bike', 'van')
);
于 2011-06-16T04:41:47.327 回答
5

您将使用检查约束。在 SQL Server 中它是这样工作的

ALTER TABLE Vehicles
ADD CONSTRAINT chkVehicleType CHECK (VehicleType in ('car','bike','van'));

我不确定这是否是 ANSI 标准,但我确信 MySQL 具有类似的构造。

于 2011-06-16T04:35:59.553 回答
2

如果要进行 DB 端验证,可以使用触发器。有关SQLite,请参阅内容,以及有关 MySQL的详细操作方法。

所以问题是你是否应该使用数据库验证。如果您有多个客户端——无论它们是不同的程序,还是多个用户(可能有不同版本的程序)——那么走数据库路线绝对是最好的。数据库(希望)是集中式的,因此您可以解耦验证的一些细节。在您的特定情况下,您可以验证插入列中的值是否包含在一个单独的表中,该表仅列出有效值。

另一方面,如果您对数据库没有多少经验,计划针对几个不同的数据库,并且没有时间开发专业知识,那么简单的应用程序级别验证可能是最方便的选择。

于 2011-06-16T04:35:59.663 回答