我有2个表 - 导入和模板,模板表有3个类别。我需要从Import到Template插入类别,但Import只有一列。
从图片来看,它应该只插入5个类别,因为有5个不同的类别。有2个sub1类和1个sub2类。模板表中的CSD_ID是自动生成的。 insert语句应使用其父CSD_ID更新Primary_Cat_Id。
示例,厕所是国内的sub2,所以它应该获得国内的CSD_ID并填充在Primary_Cat_Id中,但它也是Bath的sub1,所以它应该获得Bath的CSD_ID并将其填入Parent_ID。
Last_Lev为1或0. 1表示它是最后一级,0表示它下面有子类别
答案 0 :(得分:1)
您可以通过在Template表上创建AFTER INSERT
触发器来实现此目的,这样当您从Import表中插入时,它将更新Parent_Id
的值,{{1 }},Lev_No
和Primary_Cat_Id
会自动生成。
我假设你的表结构看起来像这样:
Last_Lev
您的触发器应如下所示:
IF OBJECT_ID('Import', 'U') IS NOT NULL DROP TABLE Import;
CREATE TABLE Import (
[Main Category] VARCHAR(255) -- NOT NULL?
, [Sub Category 1] VARCHAR(255)
, [Sub Category 2] VARCHAR(255));
INSERT Import
VALUES ('Domestic', NULL, NULL)
, ('Domestic', 'House', NULL)
, ('Domestic', NULL, NULL)
, ('Domestic', NULL, NULL)
, ('Domestic', 'Bath', 'Toilet')
, ('Domestic', NULL, NULL)
, ('Commercial', NULL, NULL)
, ('Commercial', NULL, NULL)
, ('Commercial', NULL, NULL)
, ('Commercial', NULL, NULL)
, ('Commercial', NULL, NULL)
, ('Commercial', NULL, NULL);
IF OBJECT_ID('Template', 'U') IS NOT NULL DROP TABLE Template;
CREATE TABLE Template (
CSD_ID INT IDENTITY (1, 1) PRIMARY KEY
, Category VARCHAR(255) NOT NULL
, Parent_Id INT
, Lev_No INT
, Primary_Cat_Id INT
, Last_Lev BIT);
可能有一种更简单的方法可以做到这一点,但这在技术上有效(至少对于样本数据)。
之后,您只需要一个光标或其他东西来逐个进行插入,从主要类别开始:
IF OBJECT_ID('tr_Template_Insert', 'TR') IS NOT NULL DROP TRIGGER tr_Template_Insert;
GO
CREATE TRIGGER tr_Template_Insert
ON Template
AFTER INSERT
AS BEGIN
WITH CTE AS (
SELECT RN, cats, lvl
FROM (
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) RN
FROM Import) T
CROSS APPLY (
VALUES ([Main Category], 1)
, ([Sub Category 1], 2)
, ([Sub Category 2], 3)) S(cats,lvl)
WHERE S.cats IS NOT NULL
)
UPDATE T
SET Last_Lev = Z.lastLev
, Primary_Cat_Id = COALESCE(Z.PrimaryCat, T.CSD_ID)
, Parent_Id = COALESCE(Z.ParentCat, T.CSD_ID)
, Lev_No = Z.levNo
FROM Template T
JOIN (
SELECT C.cats
, MAX(CASE WHEN C.lvl = LL.lastlev THEN 1 ELSE 0 END) lastLev
, MAX(Pri.primarycat) PrimaryCat
, MAX(Par.parentcat) ParentCat
, MAX(lvl) levNo
FROM CTE C
JOIN inserted I ON I.Category = C.cats
OUTER APPLY (
SELECT T.CSD_ID
FROM CTE CZ
JOIN Template T ON T.Category = CZ.cats
WHERE CZ.RN = C.RN
AND CZ.lvl = 1) Pri(primarycat)
OUTER APPLY (
SELECT T.CSD_ID
FROM CTE CZ
JOIN Template T ON T.Category = CZ.cats
WHERE CZ.RN = C.RN
AND CZ.lvl = C.lvl-1) Par(parentcat)
OUTER APPLY (
SELECT MAX(lvl)
FROM CTE CZ
WHERE CZ.RN = C.RN) LL(lastlev)
GROUP BY C.cats) Z ON Z.cats = T.Category;
END
光标将插入主类别,然后是子类别1,然后是子类别2,触发器将填充其余值。