首页 > 解决方案 > 对唯一字符和其他列使用 CHECK 约束 PostgresSQL

问题描述

我有一个名为 STAFF 的设计表,其中包含 3 列用于 PostgreSQL。

staffId VARCHAR(6) PK,
firstName VARCHAR(50),
lastName VARCHAR(50)

我想建立一个检查约束,使staffId的前2个字母必须匹配firstName的第一个字母和lastName的第一个字母,并且最后四个数字不能与staffId中的另一个条目相同。

例如

John Smith - JS0001,
Lisa Jones - LJ0002

因此,如果 Joanne Smith 加入团队,那么 JS0002 将失败,因为 Lisa Jones 已经拥有 0002。

我怎样才能做到这一点?

非常感谢。

标签: sqlpostgresqlconstraints

解决方案


这似乎不是好的数据库设计。您应该简单地声明StaffId为一serial列并让它成为一个整数。瞧!就这样完成了。

对于外键引用,整数通常比字符串更有效。他们还唯一标识员工,即使他们的名字发生了变化。

例如,在我居住的国家,女性(经常)和男性(有时)在结婚或离婚时改名。那将完全抛弃你的计划。

综上所述,你可以做你想做的事情uniquecheck约束:

alter table staff add constraint chk_staffId
    check (substr(staffId, 1, 1) = substr(firstname, 1, 1) and
           substr(staffId, 2, 1) = substr(lastname, 1, 1) and
           staffId ~ '^[A-Z][A-Z][0-9]{4}$'
          );

然后约束将被实现为表达式的索引:

create index unq_staffId_number on (substr(staffid, 3, 4));

推荐阅读