我正在使用Visual Studio 2008,C#,LINQ to SQL,并使用数据库dbml GUI编辑器来创建数据库。我想创建一对多关系,但在我的情况下,1对象有2个主键。使用GUI edtior我创建了关联,但是当程序运行并创建数据库时,我收到错误:
“引用的表必须具有主键或候选键。[FK Name = Screen_Pixel]”
dbml中创建的XML如下所示:
<Table Name="Screen">
<Column Name="PKA1" Type="System.Int64" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PKA2" Type="System.Int32" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Association Name="Screen_Pixel" Member="Pixels" ThisKey="PKA1,PKA2" OtherKey="PKB1,PKB2" Type="Pixel" />
</Table>
<Table Name="Pixel>
<Column Name="PKB1" Type="System.Int64" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PKB2" Type="System.Int32" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PKB3" Type="System.Int32" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Association Name="Screen_Pixel" Member="Screen" ThisKey="PKB1,PKB2" OtherKey="PKA1,PKA2" Type="Screen" IsForeignKey="true" />
</Table>
C#代码中生成的关联是:
[Association(Name=@"Screen_Pixel", Storage=@"_Screen", ThisKey=@"PKA1,PKA2", OtherKey=@"PKB1,PKB2", IsForeignKey=true)]
[Association(Name=@"Screen_Pixel", Storage=@"_Pixels", ThisKey=@"PKB1,PKB2", OtherKey=@"PKA1,PKA2")]
有什么想法吗?
答案 0 :(得分:1)
由于我一直在努力寻找类似的东西并且这个问题接近我的问题,我将在这里加上我的2美分用于下一个可能遇到相同问题的灵魂(在运行时从对象模型创建数据库) )。
如果您的复合键实际上不必是主键(即您只想提供组合的唯一性),解决方案是:
通过DataContext上的附加步骤提供唯一性约束,例如:
yourDataContext.ExecuteCommand("ALTER TABLE Stuff ADD UNIQUE (unique_thing_1, unique_thing_2, unique_thihng_3)");
之后提交将在尝试插入重复字段时抛出异常。
答案 1 :(得分:0)
为什么你要为主要字段使用多个字段(也称为“复合主要字段”)?
一些学校和书籍教授使用“复合主键”,但实际上,它们并不是一个好主意。许多软件不允许使用这些字段,即使这样,也很难处理。
使用单个字段主键总是更好。
我的建议是,将这些字段保留为标准字段或外键,添加新字段,自动分配或增加。
示例:
<Table Name="Screen"> <Column Name="ScreenKey" Type="System.Int64" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Column Name="ScreenField1" Type="System.Int64" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Column Name="ScreenField2" Type="System.Int32" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Association Name="Screen_Pixel" Member="Pixels" ThisKey="ScreenKey" OtherKey="ScreenKey" Type="Pixel" />
</Table>
<Table Name="Pixel>
<Column Name="PixelKey" Type="System.Int64" IsPrimaryKey="true" CanBeNull="false" UpdateCheck="Never" />
<Column Name="ScreenKey" Type="System.Int64" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PixelField1" Type="System.Int64" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PixelField2" Type="System.Int32" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Column Name="PixelField3" Type="System.Int32" IsPrimaryKey="false" CanBeNull="false" UpdateCheck="Never" />
<Association Name="Screen_Pixel" Member="Screen" ThisKey="ScreenKey" OtherKey="ScreenKey" Type="Screen" IsForeignKey="true" />
</Table>