2

我目前的任务是在无法更改架构的数据库上进行项目。我需要在需要唯一 ID 的表中插入一个新行,但该结构的原始创建者并未将此值设置为自动增量。为了解决这个问题,我一直在使用类似于:

(SELECT TOP 1 [ID] from [Table] ORDER BY [ID] DESC) + 1

在给出 ID 字段的值时,基本上有一个内部查询。问题是几行下来,我需要我刚刚输入的那个 ID。如果我可以为该列设置一个 SQLParameter 来输出,我可以获得它设置的值,问题是我使用的是 SQL,而不是像我使用其他 SQLParameters 那样的硬值。我不能使用 SQL 来代替一个值吗?

这是一个潜在的大容量交换,所以我宁愿不做 2 个不同的查询(一个用来获取 id,一个用来插入)。

4

4 回答 4

3

您说您无法更改架构,但是您可以向执行自动增量列的项目添加一个附加表吗?然后,您可以使用该表(安全地)创建新 ID 并将它们返回给您的代码。

这类似于 Oracle 处理 ID 的方式,有时也在 Oracle 上运行的 sql server 供应商应用程序将使用这种方法来帮助最小化两个数据库之间的差异。

更新:
啊,我刚刚发现您对此处其他答案的评论。在这种情况下,我认为唯一可行的另一件事是将您的两个语句(插入一个新 ID,然后读回新 ID)放在具有SERIALIZABLE隔离级别的事务中。这有点糟糕,因为它让你对性能和锁定问题持开放态度。

于 2011-09-06T21:46:10.817 回答
1

您是否可以在数据库中创建一个存储过程来执行此操作,然后存储过程的返回值将返回您需要的 ID?

于 2011-09-06T21:23:32.083 回答
1

我对您需要在哪里使用此 ID 感到有些困惑。如果它在同一个存储过程中,只需使用此方法:

DECLARE @NewId int
SELECT TOP 1 @NewId =  [ID] + 1 from [Table] ORDER BY [ID] DESC
SELECT @NewId
于 2011-09-06T21:49:16.933 回答
0

您可以在单个 SqlCommand 中放置多个 SQL 语句。因此,您可以轻松地按照 Abe 的建议做一些事情:

DECLARE @NewId int
SELECT TOP 1 @NewId =  [ID] + 1 from [Table] ORDER BY [ID] DESC
INSERT INTO [Table] (ID, ...) VALUES (@NewId, ...)
SELECT @NewId

然后您只需在 SqlCommand 上调用 ExecuteScalar,它就会执行 INSERT,然后返回它使用的 ID。

于 2011-09-06T21:56:12.277 回答