我有一个由分区ID分区的巨大表。每个分区在其唯一约束中可以具有不同数量的字段。考虑一下这个表:
+----+---------+-------+-----+--+
| id | part_id | name | age | |
+----+---------+-------+-----+--+
| 1 | 1 | James | 12 | |
+----+---------+-------+-----+--+
| 2 | 1 | Mary | 33 | |
+----+---------+-------+-----+--+
| 3 | 2 | James | 1 | |
+----+---------+-------+-----+--+
| 4 | 2 | Mike | 19 | |
+----+---------+-------+-----+--+
| 5 | 3 | James | 12 | |
+----+---------+-------+-----+--+
对于part_id: 1
我需要对字段name and age
设置唯一约束。 part_id: 2
需要name
的唯一约束。 part_id: 3
需要name
的唯一约束。我对任何可以实现此目的的数据库持开放态度。
答案 0 :(得分:1)
Classic RDBMS旨在使用稳定的架构。这意味着表,列,索引,关系的结构不会经常更改,每个表都有固定数量的具有固定类型的列,并且使它们动态化是困难/低效的。
SQL Server有filtered indexes。
因此,您可以为每个分区创建单独的唯一索引。
CREATE UNIQUE NONCLUSTERED INDEX IX_Part1 ON YourTable
(
name ASC,
age ASC
)
WHERE (part_id = 1)
CREATE UNIQUE NONCLUSTERED INDEX IX_Part2 ON YourTable
(
name ASC
)
WHERE (part_id = 2)
CREATE UNIQUE NONCLUSTERED INDEX IX_Part3 ON YourTable
(
name ASC
)
WHERE (part_id = 3)
这些DDL语句是静态的,part_id
的值是硬编码的。 Optimiser能够在具有相同WHERE
过滤器的查询中使用此类索引,因此它们不仅可用于强制执行约束。
您始终可以编写一个程序,动态生成CREATE INDEX
语句的文本,并通过EXEC
/ sp_executesql
运行。 YourTable
上可能会有一些聪明的触发器用于动态创建它,因为表中的数据会发生变化,但最后它将是一些静态CREATE INDEX
语句。
您可以提前为part_id
的所有可能值创建这些索引,即使表中还没有这样的实际值。
如果您有数千个part_id
并且想要创建数千个此类唯一约束,那么您当前的架构可能不太合适。
SQL Server允许每个表最多999个非聚簇索引。请参阅Maximum Capacity Specifications for SQL Server。
您是否尝试构建EAV (entity-attribute-value) model的某些变体?
也许有非关系型DBMS允许更大的灵活性,更适合您的任务,但我没有经验。
答案 1 :(得分:0)
在oracle中,下面可以动态创建唯一索引
edi