programing

SQL Output 절에서 삽입되지 않은 열을 반환할 수 있습니까?

instargram 2023. 4. 7. 20:51
반응형

SQL Output 절에서 삽입되지 않은 열을 반환할 수 있습니까?

데이터베이스를 일부 수정했으며 이전 데이터를 새 테이블로 마이그레이션해야 합니다.그러기 위해서는 테이블을 채워야 합니다.ReportOptions) 원래 테이블에서 데이터를 가져옵니다(Practice두 번째 중간 테이블을 채웁니다( ).PracticeReportOption).

ReportOption (
    ReportOptionId int PK, 
    field1, field2...
)
Practice (
    PracticeId int PK, 
    field1, field2...
)
PracticeReportOption (
    PracticeReportOptionId int PK, 
    PracticeId int FK, 
    ReportOptionId int FK, 
    field1, field2...
)

이동에 필요한 모든 데이터를 얻기 위해 쿼리를 작성했습니다.Practice로.ReportOptions하지만 중간 표를 채우는데 어려움을 겪고 있습니다.

--Auxiliary tables
DECLARE @ReportOption TABLE (
    PracticeId int, -- This field is not on the actual ReportOption table
    field1, field2...
)
DECLARE @PracticeReportOption TABLE (
    PracticeId int, 
    ReportOptionId int, 
    field1, field2
)

--First I get all the data I need to move
INSERT INTO @ReportOption
SELECT P.practiceId, field1, field2...
  FROM Practice P

--I insert it into the new table,
--but somehow I need to have the repation PracticeId / ReportOptionId
INSERT INTO ReportOption (field1, field2...)
OUTPUT @ReportOption.PracticeId, --> this is the field I don't know how to get
       inserted.ReportOptionId
  INTO @PracticeReportOption (PracticeId, ReportOptionId)
SELECT field1, field2
  FROM @ReportOption

-- This would insert the relationship, If I knew how to get it!
INSERT INTO @PracticeReportOption (PracticeId, ReportOptionId)
SELECT PracticeId, ReportOptionId
  FROM @ReportOption

의 행선지 테이블에 없는 필드를 참조할 수 있는 경우OUTPUT조항, 그게 좋을 것 같아요(못할 것 같은데, 확실히는 모르겠어요).내 욕구를 어떻게 충족시킬지 생각나는 거 없어?

다음을 사용하여 이 작업을 수행할 수 있습니다.MERGE대신INSERT.

그럼, 이것을 대체해 주세요.

INSERT INTO ReportOption (field1, field2...)
OUTPUT @ReportOption.PracticeId, --> this is the field I don't know how to get
       inserted.ReportOptionId
  INTO @PracticeReportOption (PracticeId, ReportOptionId)
SELECT field1, field2
  FROM @ReportOption

포함:

MERGE INTO ReportOption USING @ReportOption AS temp ON 1 = 0
WHEN NOT MATCHED THEN
    INSERT (field1, field2)
    VALUES (temp.Field1, temp.Field2)
    OUTPUT temp.PracticeId, inserted.ReportOptionId, inserted.Field1, inserted.Field2
    INTO @PracticeReportOption (PracticeId, ReportOptionId, Field1, Field2);

중요한 것은 절대 참이 되지 않는 술어를 사용하는 것입니다.1 = 0는, 항상 삽입을 실행하지만, 송신원테이블과 행선지 테이블의 양쪽의 필드에 액세스 할 수 있습니다.


테스트에 사용한 코드는 다음과 같습니다.

CREATE TABLE ReportOption (
    ReportOptionID INT IDENTITY(1, 1), 
    Field1 INT, 
    Field2 INT
)
CREATE TABLE Practice (
    PracticeID INT IDENTITY(1, 1), 
    Field1 INT, 
    Field2 INT
)
CREATE TABLE PracticeReportOption (
    PracticeReportOptionID INT IDENTITY(1, 1), 
    PracticeID INT, 
    ReportOptionID INT, 
    Field1 INT, 
    Field2 INT
)

INSERT INTO Practice VALUES (1, 1), (2, 2), (3, 3), (4, 4)


MERGE INTO ReportOption r USING Practice p ON 1 = 0
WHEN NOT MATCHED THEN
    INSERT (field1, field2)
    VALUES (p.Field1, p.Field2)
    OUTPUT p.PracticeId, inserted.ReportOptionId, inserted.Field1, inserted.Field2
    INTO PracticeReportOption (PracticeId, ReportOptionId, Field1, Field2);

SELECT *
FROM PracticeReportOption

DROP TABLE ReportOption
DROP TABLE Practice
DROP TABLE PracticeReportOption 

더 읽어보면, 내가 아는 모든 것의 출처는 여기야.

MS SQL Server 2005 이하를 사용하는 사용자는 이 답변이 도움이 될 수 있습니다.


MERGE는 SQL Server 2008 이후에서만 작동합니다.

그 외에는 매핑테이블을 작성할 수 있는 다른 회피책을 찾았습니다.

SQL 2005의 해상도는 다음과 같습니다.

DECLARE @ReportOption TABLE (
    ReportOptionID INT IDENTITY(1, 1), 
    Field1 INT, 
    Field2 INT
)
DECLARE @Practice TABLE(
    PracticeID INT IDENTITY(1, 1), 
    Field1 INT, 
    Field2 INT
)
DECLARE @PracticeReportOption TABLE(
    PracticeReportOptionID INT IDENTITY(1, 1),
    PracticeID INT, 
    ReportOptionID INT, 
    Field1 INT, 
    Field2 INT
)

INSERT INTO @Practice (Field1, Field2) VALUES (1, 1)
INSERT INTO @Practice (Field1, Field2) VALUES (2, 2)
INSERT INTO @Practice (Field1, Field2) VALUES (3, 3)
INSERT INTO @Practice (Field1, Field2) VALUES (4, 4)

INSERT INTO @ReportOption (field1, field2)
    OUTPUT INSERTED.ReportOptionID, INSERTED.Field1, INSERTED.Field2 
        INTO @PracticeReportOption (ReportOptionID, Field1, Field2)
    SELECT Field1, Field2 
    FROM @Practice 
    ORDER BY PracticeID ASC;


WITH CTE AS ( 
    SELECT PracticeID, 
        ROW_NUMBER() OVER ( ORDER BY PracticeID ASC ) AS ROW 
    FROM @Practice
)
UPDATE M 
SET M.PracticeID = S.PracticeID 
FROM @PracticeReportOption AS M
JOIN CTE AS S ON S.ROW = M.PracticeReportOptionID

SELECT * FROM @PracticeReportOption

주요 요령은 소스 테이블과 타깃 테이블의 정렬된 데이터로 매핑 테이블을 두 번 채우는 것입니다.

자세한 내용은 SQL Server 2005에서 OUTPUT을 사용하여 삽입된 데이터 병합을 참조하십시오.

언급URL : https://stackoverflow.com/questions/10949730/is-it-possible-to-for-sql-output-clause-to-return-a-column-not-being-inserted

반응형