2017-01-16 2 views
0

Я пытаюсь получить запрос, который может помочь мне достичь что-то похожее на изображение ниже:SQL Server: разбиении строки на несколько строк из пункта OUTPUT

Output result set

Первая таблица является результатом предложение SQL OUTPUT (оба вставлены и удалены). Я хотел бы разбить эти результаты на новую таблицу (например, вторую на приведенном выше рисунке). Поэтому я хочу иметь одну строку, изображающую вставленные записи, и вторую строку, изображающую удаленные записи.

Это, как был создан мой образец данных:

select 
    inserted_ID = 1, 
    inserted_name = 'Brian', 
    inserted_phone = '123-456-7890', 
    operation_type1 = 'inserted', 
    deleted_id = 2, 
    deleted_name = 'James', 
    deleted_phone = '222-222-2222', 
    operation_type2 = 'Deleted' 
into 
    #tbltest 
+0

Просим выслать [Minimal, Co mplete и Подтверждаемый пример] (http://stackoverflow.com/help/mcve) также проверьте [Как спросить] (http://stackoverflow.com/help/how-to-ask). – wdosanjos

+0

Почему у вас есть такая структура таблицы, как это в первую очередь? Кажется «странным» иметь «Inserted_ID» и «Deleted_ID» в той же строке. Есть ли какие-либо фактические/естественные отношения между этими двумя? –

+0

Hi @srutzky. Это действительно просто пример. Это не настоящая таблица в моей базе данных. Кроме того, при использовании предложения OUTPUT с инструкцией UPDATE SQL Server позволяет нам показывать как вставленную запись, так и удаленную запись. – Solution

ответ

0
  1. Если вы не используете MERGE заявление, вы оба не INSERT и DELETE в одной и той же операции DML может. Единственный раз (за пределами MERGE), что у вас будут строки в псевдо таблицах inserted и deleted во время операции UPDATE, и в этом случае строки в обоих будут ссылаться на одни и те же фактические строки в таблицах, до и после просмотров этих строк. Значит, вы не увидите значений, подобных тем, что показано в вопросе, где Inserted_ID и Deleted_ID отличаются.

  2. Если вы используете MERGE, то у вас уже должны быть строки в нужном формате, поскольку одна строка из предложения OUTPUT не будет представлять собой несколько затронутых строк. Значение: OUTPUT уже работает, вы хотите этого, а не так, как вы заявляете, что он это делает.

0

Попробуйте использовать OUTER/CROSS ОТНОСИТЬСЯ оператор:

select ... 
from #Output/@Output as o 
cross apply (
    select o.insertedColA, o.insertedColB, 'I' 
    -- where o.insertedID is not null 
    union all 
    select o.deletedColB, ..., 'D' 
    -- where o.deletedID is not null 
) as x(ColA, ColB, RowType) 
0

Попробовать организовать свою структуру таблицы что-то вроде (держать внимание на [UID]):

create table [my_table] 
(
    [id]  int 
    ,[name]  nvarchar(256) 
    ,[phone] nvarchar(256) 
); 

insert into [my_table] 
values (1, 'Brian', '123-456-7890'); 

create table [my_log] 
(
    [inserted_id]  int 
    ,[inserted_name] nvarchar(256) 
    ,[inserted_phone] nvarchar(256) 
    ,[deleted_id]  int 
    ,[deleted_name]  nvarchar(256) 
    ,[deleted_phone] nvarchar(256) 
    ,[uid]    uniqueidentifier primary key  
); 

А потом это решает вашу проблему:

update [my_table] 
set [id]  = 2   
    ,[name] = 'James' 
    ,[phone] = '222-222-2222' 
output 
    [deleted].[id] 
    ,[deleted].[name] 
    ,[deleted].[phone] 
    ,[inserted].[id] 
    ,[inserted].[name] 
    ,[inserted].[phone] 
    ,newid() 
into [my_log] 
(
    [inserted_id] 
    ,[inserted_name] 
    ,[inserted_phone] 
    ,[deleted_id] 
    ,[deleted_name] 
    ,[deleted_phone]  
    ,[uid] 
); 

select 
    [id]  = [id] 
    ,[name]  = [name] 
    ,[phone] = [phone] 
    ,[op_type] = CASE [op_type] WHEN 0 THEN 'Insert' ELSE 'Delete' END 
from  
    ( 
     select 
      [id]  = [inserted_id] 
      ,[name]  = [inserted_name] 
      ,[phone] = [inserted_phone] 
      ,[op_type] = 0 -- insert 
      ,[uid]  = [uid] 
     from 
      [my_log] 
     union 
     select 
      [id]  = [deleted_id] 
      ,[name]  = [deleted_name] 
      ,[phone] = [deleted_phone] 
      ,[op_type] = 1 -- delete 
      ,[uid]  = [uid] 
     from 
      [my_log] 
    ) as [l] 
order by 
    [l].[uid] 
    ,[l].[op_type] ASC; 
+0

Спасибо @Juozas, это более сложный ответ, и он работал отлично. Я не могу отметить как ответ, потому что я новичок в quora, поэтому он не позволит мне. Но спасибо большое! – Solution

+0

Спасибо за интересный вопрос! – Juozas