C# 实体框架存储过程插入自定义序列号

C# 实体框架存储过程插入自定义序列号,c#,.net,entity-framework-4,C#,.net,Entity Framework 4,请耐心听我的解释 我有一个在EF4中使用映射存储设置表的过程来插入数据 例如: id | location | type 1 | 10 | 15 5 | 10 | 16 SP所做的是在另一个表中检查下一个按位置和类型对应的id 所以在这个例子中,下一个id是 2用于位置10和类型15 6位置10类型16 这是通过在EF中映射结果列来实现的 除非两个不同的键具有相同的序列号,否则它工作正常。例如: id | location |

请耐心听我的解释

我有一个在EF4中使用映射存储设置表的过程来插入数据

例如:

    id | location | type
    1  |     10   |  15
    5  |     10   |  16
SP所做的是在另一个表中检查下一个按位置和类型对应的id

所以在这个例子中,下一个id是

  • 2用于位置10和类型15
  • 6位置10类型16
这是通过在EF中映射结果列来实现的

除非两个不同的键具有相同的序列号,否则它工作正常。例如:

    id | location | type
    1  |     10   |  11
    1  |     10   |  10
编辑:当我同时创建两个新行时,会发生此错误

它们的下一个值都是2,数据保存到数据库中,但应用程序失败,并显示以下消息:

已成功提交对数据库的更改,但出现错误 更新对象上下文时。ObjectContext可能位于 状态不一致。
内部异常消息:
AcceptChanges无法继续,因为对象的键值与其他键值冲突 ObjectStateManager中的对象。
在调用AcceptChanges之前,请确保键值是唯一的

有什么建议吗

编辑 存储过程示例

声明@nextnumberint

从位置=@location和类型=@type的顺序_表中选择@nextNumber=value+1

将值(@location,@type,@nextnumber,…)插入表(location,type,id,…)中

更新顺序_表集值=@nextNumber,其中位置=@location,类型=@type

选择@nextNumber作为[nextNumber]


这听起来像是你在错误地使用id列,而不仅仅是指“自动递增int”。

而不知道更多关于设计的信息;您可以修改表,使ID不是主键,而是将ID/Location/Type集用作复合键。

伪负数是一个很好的技巧,在DataSet/TableAdapter时代工作得非常好。如果这不起作用,可能这是一个竞争条件,您需要将详细信息放在事务中,以便在完成递增和插入您的id之前,其他线程/行无法获取下一个id。

尝试将伪负键分配给新实体。像-1,-2,所以EF可以将它们分开。嗨,这就是它的设置方式,ID/位置/类型所有这些都是keyIs ID在数据库中被无意中设置为主键吗?不,唯一的主键是3的组合。你能解释一下你的评论吗?我添加了一个我正在使用的sp的示例。通常,一个sp有一个列,该列纯粹是行的唯一标识符。(遗憾的是术语“unique identifier”被重载,通常表示“Guid”。我没有使用该定义,而只是使用“unique”。)通常此列被命名为Id或just Id。在您的用例中,Id列表示“位置/类型序列”,并且没有“unique”列。