非规范化多对多映射
在 SQL Server 2008 R2 中,我有一个具有以下结构的表
(
Id INT NOT NULL PRIMARY KEY,
Left1 INT NOT NULL,
Left2 INT NULL,
Right1 NVARCHAR(128) NOT NULL,
Right2 NVARCHAR(128) NOT NULL,
Right3 NVARCHAR(128) NULL,
Right4 NVARCHAR(128) NULL,
Right5 NVARCHAR(128) NULL,
Right6 NVARCHAR(128) NULL
)
,用于将来自系统(“左”)的 Left1 和 Left2 映射到 Right1-6,转到另一个系统(“右”)。
我需要确保左列是唯一的,这是我使用唯一索引完成的,并且左右组合也是唯一的。
我无法在此处使用索引,因为支持的最大列大小为 900 字节。我需要避免将表拆分为“左”、“右”和“左到右”——因为对于我的用例来说,这太乏味且容易出错。
强制组合唯一性的正确方法是什么?
我的要求是:
- 在整个表中,不得有具有相同 Left1 和 Left2 值的行(已解决)
- 在整个表中,不得有具有相同 Left1、Left2、Right1、Right2、Right3、Right4 值的行, Right5,Right6(我需要帮助)
In SQL Server 2008 R2 I have a table with the following structure
(
Id INT NOT NULL PRIMARY KEY,
Left1 INT NOT NULL,
Left2 INT NULL,
Right1 NVARCHAR(128) NOT NULL,
Right2 NVARCHAR(128) NOT NULL,
Right3 NVARCHAR(128) NULL,
Right4 NVARCHAR(128) NULL,
Right5 NVARCHAR(128) NULL,
Right6 NVARCHAR(128) NULL
)
Which is used to map Left1 and Left2, coming from a system ("Left") into Right1-6, going to another system ("Right").
I need to ensure that the Left columns are unique, which I have done with a unique index, and that the Left-Right combinations are also unique.
I cannot use an index here because the maximum column size supported is 900 bytes. I need to avoid splitting the table in Left, Right and Left2Right - as it's way too tedious and error prone with my use cases.
What is the correct way of enforcing the uniqueness of the combination?
My requirements are:
- In the whole table there MUST be no rows with the same values for Left1 and Left2 (solved)
- In the whole table there MUST be no rows with the same values for Left1, Left2, Right1, Right2, Right3, Right4, Right5, Right6 (I need help here)
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
完全没有必要添加第二个约束。
的唯一约束
对
Left1, Left2
将防止
Left1, Left2, Right1, Right2, Right3, Right4,右5,右6。
如果不先复制前 2 个字段,就无法复制所有 8 个字段。
It's completely unnecessary to add a second constraint.
Your unique constraint on
Left1, Left2
will prevent duplicate values of
Left1, Left2, Right1, Right2, Right3, Right4, Right5, Right6
.There is no way to duplicate all 8 of those fields without first duplicating the first 2.
一个想法:创建所有可能的“Right”值的查找表,为它们分配整数代理键,在 Left2Right 表中使用这些代理键,并在它们上构建唯一约束。非规范化和丑陋如罪恶,但它可以解决问题。
(已添加)
您还可以尝试构建值的哈希值并对其进行约束。穷人的版本是使用校验和添加计算行:
并在其上添加唯一约束(它可能必须是持久计算列才能执行此操作)。这样做的主要问题是不同的初始值集可能会产生相同的校验和值。您可以通过 hashbytes 函数使用一种(更加)强大的哈希算法,该算法具有相同的限制(可能存在重复的哈希值),但冲突的机会会小得多。
One idea: create a lookup table of all possible "Right" values, assign them integer surrogate keys, use those surrogate keys in your Left2Right table, and build your unique constraint on them. Denormalized and ugly as sin, but it could do the trick.
(Added)
You could also try building a hash of the values and constraining on that. The poor mans’ version would be to add a calcluated row using checksum:
and add a unique constraint on that (it may have to be a persisted calculated column to do this). The main problem with this is that different sets of initial values could produce the same checksum values. You could use one of the (much more) robust hashing algorithms via the hashbytes function, which would have the same limitation (possible duplicate hash values) but the chance of collision would be significantly smaller.