为啥填充数据表时缺少唯一约束?
Posted
技术标签:
【中文标题】为啥填充数据表时缺少唯一约束?【英文标题】:Why is the unique constraint missing when filling the datatable?为什么填充数据表时缺少唯一约束? 【发布时间】:2017-08-15 12:32:54 【问题描述】:我在 SQL server 中有下表
projects
id(PK, int, not null)
name (varchar(255), not null)
public_key_token (varchar(50), null)
我使用
向name
列添加了唯一约束
ALTER TABLE dbo.projects
ADD CONSTRAINT name_unique UNIQUE (name);
这会导致表上出现Unique, Non-Clustered
索引(信任 SSMS)。
在代码中,我正在使用检索表数据
using (SqlDataAdapter adapter = new SqlDataAdapter("select * from " + DbTabName, con))
using (DataTable table = new DataTable(DbTabName))
DataTable dt = adapter.FillSchema(table, SchemaType.Source);
PkColumns = dt.PrimaryKey.Select(c => c.ColumnName).ToList();
AutoIncrementColumns = dt.PrimaryKey.Where(c => c.AutoIncrement).Select(c => c.ColumnName).ToList();
UniqueColumns = dt.Columns.Cast<DataColumn>().Where(c => c.Unique).Select(c => c.ColumnName).ToList();
...
PK 和 AutoIncrement 列都可以,但在 UniqueColumns
中,我只能再次获得 PK 列。
name
列到达 C# 时没有 Unique
约束。
将SchemaType
更改为Mapped
并没有改变结果。
为什么我在通往 C# 的路上失去了这个约束?我是否遗漏了 SQL Server 端或 C# 中的某些内容?
[更新] @Tim-Schmelter 的回答只能解决一半问题。
仅添加索引不起作用。当id
列上的PK存在时添加索引也不起作用。
我让它工作的唯一方法是删除表,在没有任何键和索引的情况下重新创建它,然后添加 unique
索引,如蒂姆的回答。但是,在再次为 id
列添加 PK 后,我又回到了仅将 id
列为唯一列的旧行为。
这真的很奇怪。
【问题讨论】:
在一些(奇怪的)地方,一些代码区分了 column 约束和 table 约束。由于单独的ALTER TABLE
创建了一个表约束,它是否仅存在于DataTable
s Constraint
属性中? (由于表约束可以应用于多个列,如果它们是多列唯一约束的一部分,则不适合标记单个列的 Unique
属性)
从我的(有限的)实验来看,系统似乎只处理(最多)一个约束,而 PK 优先于其他约束。我找不到任何文档来说明这是否是预期的行为。
@Damien_The_Unbeliever 这也是我现在的想法。现在我将name
列标记为PK,而将id
排除在外。也许我可以在 MS tech net 上获得一些额外的反馈。
@MarkusDeibel:奇怪,我的测试表有一个 id 列,它是主键和 name 列上的唯一索引。 DataColumn 的 Unique
-property 在该列上按预期设置为 true,有或没有主键
【参考方案1】:
使用此create a unique index 或使用 SSMS 的 gui。
CREATE UNIQUE NONCLUSTERED INDEX [name_unique] ON [dbo].[projects]
(
name ASC
)
您添加了唯一约束而不是唯一索引。
您的代码现在成功检索到UniqueColumns
(单列name
)。
【讨论】:
以上是关于为啥填充数据表时缺少唯一约束?的主要内容,如果未能解决你的问题,请参考以下文章