0
我有一个非常通用的一套存储所有的数据,其工作出色的三个表(我们所说的少量数据在这里)SQL服务器:递归存储过程
DataContainer - 管理“记录”
PK - DataContainerId
FK - ParentDataContainerId
FM - ModelEntityId
DataInstance - 管理版本
PK - DataInstanceId
FK - DataContainerId
IsCurrent [bit] NOT NULL CONSTRAINT [DF_DataInstance_IsCurrent] DEFAULT ((1)),
ModifiedBy [nvarchar](50) NOT NULL CONSTRAINT [DF_DataInstance_ModifiedBy] DEFAULT (suser_sname()),
ModifiedDateTime [datetime] NOT NULL CONSTRAINT [DF_DataInstance_ModifiedDateTime] DEFAULT (getdate()),
DataValue
PK - DataValueId
FK - DataInstanceId
FK - ModelEntityId
ValueText --the actual values
问题:当一条记录被删除,我需要标记为删除所有子记录。
尝试
--flag current record as deleted
update DataInstance
set IsCurrent = 0
Where DataContainerId = @DataContainerId
And (@ModelContainerId is null or @ModelContainerId = ModelContainerId)
--remove all child records
declare db_cursor for
select sc.DataContainerId as 'ChildDataContainerId' from DataInstance di
inner join datacontainer dc on dc.datacontainerId = di.datacontainerId
where parentdatacontainerId = @DataContainerId
declare @ChildDataContainerId int
open db_cursor
fetch next from db_cursor into @ChildDataContainerId
while @@fetch_status = 0
begin
exec dataInstance_Delete null, @ChildDataContainerId --current sp
end
close db_cursor
deallocate db_cursor
的问题是,我不能使用游标recursivly(因为我得到一个错误,光标已经打开),所以这个SP只会工作一个级别深度。
有没有更狡猾的做法呢?
存储所有的数据在一个表中,然后使用游标来处理你的记录,你应该从脱身的做法。当你忽略规范化数据的智慧以及SQL设计的设置逻辑的力量时,你就会头痛不已。也许你应该考虑为了自己的利益重构以后的重构? – Tahbaza 2010-06-30 03:45:38
由于我讨厌贴在泥土中,只是发表负面评论,然后走开这里,如果您决定继续前进,则可以解决您的问题:使用SQL以外的应用程序编程语言进行递归。它们通常不受递归调用规则的限制,如果您更喜欢行逻辑,则可以使用记录集或同等方法更轻松地处理记录。快乐的编码... – Tahbaza 2010-06-30 03:49:19
我不得不同意Tahbaza,但如果你坚持采取这条路线,我会使用触发器。触发器可以递归执行(达到某个(可配置的我相信)级别)。 – 2010-06-30 08:01:30