TSQL插入和删除重复项以提高查询性能

时间:2016-07-29 07:14:30

标签: sql-server performance tsql

我使用这两个查询将数据首先插入到事务转储中的Transactions和表中,然后删除可能的重复项。

INSERT INTO [dbo].[Transactions_Refined]
    SELECT 
        Client_ID,
        Customer_ID,
        Transaction_ID,
        SUM(try_parse(value_sold AS numeric(18,2))) AS value_sold,
        SUM(try_parse(quantity AS numeric(18,4))) AS quantity,
        subclass,
        article,
        try_parse(Transaction_Date AS Datetime) AS Transaction_Date,
        Store_ID
    FROM 
        [dbo].[Transaction_Dump]
    GROUP BY 
        Client_ID, Customer_ID, Transaction_ID,
        try_parse(Transaction_Date AS Datetime),
        subclass, article, Store_ID ;

WITH cte AS
(
   SELECT 
       *,
       row_number() OVER(PARTITION BY Client_ID, Customer_ID, Transaction_ID, value_sold, quantity, subclass, article
                         ORDER BY Client_ID, Customer_ID, Transaction_ID, value_sold, quantity, subclass, article) AS [rn]
   FROM 
       [dbo].[Transactions_Refined]
   WHERE 
       Client_ID IN (SELECT DISTINCT [Client_ID]
                     FROM [dbo].[Transaction_Dump]) )
DELETE cte
WHERE [rn] > 1 ;

我想加快这个过程。任何的想法?我正在考虑使用外连接。

1 个答案:

答案 0 :(得分:1)

代码将文本文件中的数据导入Transaction_Dump。第一个语句中的GROUP BY负责按Client_ID,Customer_ID,Transaction_ID,Transaction_Date,子类,article,Store_ID和sums value_sold和quantity聚合各个事务。

聚合记录将插入Transaction_Refined中。我们假设这个过程会定期重复,以便最终Transaction_Refined会变得非常大。

在Transaction_Refined中插入后,会发生一些不需要的重复。 DELETE语句使用CTE删除这些重复项。 CTE对DELETE语句进行范围调整,它从Transaction_Refined中选择最新Transaction_Dump中提到的ClientId的记录。

我怀疑上面的代码中有错误。插入中的聚合在StoreId和Transaction_Date之间进行。这是有道理的。

奇怪的是,DELETE代码将删除重复项,因为不会在最新的Transaction_Dump中发生的ClientId上对StoreId和Transaction_Date进行分组。

现在重要的问题是ClientId的每个Transaction_Dump文件是否都是唯一的。我认为这不是真的,即一个ClientId可能在不同的日子有多个订单。

上面的DELETE语句基本上会丢失Transaction_Refined记录,因为它忽略了StoreId和Transaction_Date。

有两种方法可以解决这个问题:

选项1:您将Transaction_Refined视为聚合表,您可以在其中保留每天汇总的事务。在这种情况下,我们可以通过删除插入中的重复项来使DELETE语句和CTE过时。

选项2:您将Transaction_Refined视为所有StoreId和Transaction_Date上每个客户的一种总交易总数。如果是这种情况,那么应该从Transaction_Refined表中删除StoreId和Transaction_Date列,并且应该有代码来INSERT新记录或根据需要更新现有记录以保持聚合正确。

下一步将决定您是要选择选项1还是选项2.一旦有了这个,就可以很容易地制作非常有效的TSQL代码来更新Transaction_Refined表。