简体   繁体   English

从临时表更新表

[英]Update a table from a temp table

I have a table that stores formulary drug information and needs to be updated daily from a central formulary. 我有一张存储处方药物信息的表格,需要每天从中央处方集更新。 The temp table is identical to the drug table. 临时表与药物表相同。 The temp table data could be identical (and on most days will be) to the main table or it could have updated rows or new rows. 临时表数据可以与主表相同(并且在大多数情况下也是如此),或者它可以具有更新的行或新行。

I have a stored procedure to update the main table, but it fails because it won't update NULL rows (if there is a new row in the temp table). 我有一个存储过程来更新主表,但它失败,因为它不会更新NULL行(如果临时表中有一个新行)。

This is a MSSQL Server 2005. 这是一个MSSQL Server 2005。

Where am I going wrong here: 我在哪里错了:

    -- Insert statements for procedure here
UPDATE [RX_Billing].[dbo].[FS_Drug]
SET [TRADENAME] = [RX_Billing].[dbo].[FS_Drug_TEMP].[TRADENAME]
  ,[CDM] = [RX_Billing].[dbo].[FS_Drug_TEMP].[CDM]
  ,[NDC] = [RX_Billing].[dbo].[FS_Drug_TEMP].[NDC]
  ,[IP_COST] = [RX_Billing].[dbo].[FS_Drug_TEMP].[IP_COST]
  ,[OP_COST] = [RX_Billing].[dbo].[FS_Drug_TEMP].[OP_COST]
  ,[HH_COST] = [RX_Billing].[dbo].[FS_Drug_TEMP].[HH_COST]
  ,[VAR_COST] = [RX_Billing].[dbo].[FS_Drug_TEMP].[VAR_COST]
  ,[LSTUPDATE] = [RX_Billing].[dbo].[FS_Drug_TEMP].[LSTUPDATE]
FROM [RX_Billing].[dbo].[FS_Drug]
RIGHT OUTER JOIN [RX_Billing].[dbo].[FS_Drug_TEMP] ON 
          [RX_Billing].[dbo].[FS_Drug].[TRADENAME] = 
                   [RX_Billing].[dbo].[FS_Drug_TEMP].[TRADENAME]

EDIT: 编辑:

I went with Rory's code. 我选择了Rory的代码。 Thanks, that works beautifully. 谢谢,这很好用。

A note to Orion Edwards: UPSERT/MERGE is exactly what I wanted, but it is not supported under SQL Server 2005. Apparently it was planned, but didn't make that release. Orion Edwards的注释:UPSERT / MERGE正是我想要的,但SQL Server 2005不支持它。显然它是有计划的,但没有发布。 It is available in Server 2008. (From what the Interwebs has told me.) 它在Server 2008中可用。(从Interwebs告诉我的内容。)

Standard way is to do an UPDATE and then an INSERT: 标准方法是执行UPDATE然后执行INSERT:

-- UPDATE rows using an INNER JOIN with matching TRADENAME. No need to update TRADENAME column.
UPDATE drug
SET [CDM] = tmp.[CDM]
  , [NDC] = tmp.[NDC]
  , [IP_COST] = tmp.[IP_COST]
  , [OP_COST] = tmp.[OP_COST]
  , [HH_COST] = tmp.[HH_COST]
  , [VAR_COST] = tmp.[VAR_COST]
  , [LSTUPDATE] = tmp.[LSTUPDATE]
FROM [RX_Billing].[dbo].[FS_Drug] drug
INNER JOIN [RX_Billing].[dbo].[FS_Drug_TEMP] tmp  
    ON drug.[TRADENAME] = tmp.[TRADENAME]

-- Insert rows that don't have matching TRADENAME
INSERT INTO drug
SELECT 
    tmp.[TRADENAME]
  , tmp.[CDM]
  , tmp.[NDC]
  , tmp.[IP_COST]
  , tmp.[OP_COST]
  , tmp.[HH_COST]
  , tmp.[VAR_COST]
  , tmp.[LSTUPDATE]
FROM [RX_Billing].[dbo].[FS_Drug] drug
RIGHT OUTER JOIN [RX_Billing].[dbo].[FS_Drug_TEMP] tmp 
    ON  drug.[TRADENAME] = tmp.[TRADENAME]
WHERE drug.[TRADENAME] IS NULL 

You might also want to delete or flag as deleted any records in drug that aren't in tmp any more. 您可能还想删除或标记为已删除药物中不再存在于tmp中的任何记录。 Do that as a separate statement same as the UPDATE but with a LEFT OUTER JOIN where tmp.TRADENAME IS NULL. 将此作为与UPDATE相同的单独语句,但使用LEFT OUTER JOIN,其中tmp.TRADENAME为NULL。

You could try doing an UPSERT (which is basically "if exists, update, else insert"). 你可以尝试做一个UPSERT (基本上是“如果存在,更新,否则插入”)。

I believe SQL server calls it MERGE 我相信SQL服务器称之为MERGE

Wouldn't you want to do an INSERT on the new rows, and an UPDATE on existing rows? 你不想对新行进行INSERT,对现有行进行UPDATE吗? Updating this to an INNER JOIN, and adding a separate INSERT should resolve your issue if I'm understanding it correctly. 将此更新为INNER JOIN,并添加单独的INSERT应解决您的问题,如果我正确理解它。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM