我有一个包含10000行的.CSV
文件。需要将这些行插入/更新到SQL Server数据库表中。
可能存在这样的情况:数据库中可能存在几行,这意味着需要更新这些行并在日志文件中触发。如果数据库中不存在,则需要插入。
一种可能的解决方案是,我可以逐行阅读,检查数据库中的条目并相应地构建插入/更新查询。但是,此过程可能需要很长时间来创建更新/插入查询并在数据库中执行它们。有时我的CSV
文件可能有数百万条记录。
有没有其他更快的方法来实现此功能?
以下是我试图实现的代码。在这篇文章中,我将使用BULK INSERT语句进行批量导入。我们使用BULK INSERT
和MERGE
语句,因为此实现不仅用于插入记录,还用于更新记录(如果已存在)。
BULK INSERT tablename
FROM 'D:\xmlData\Trialbalelce.txt' --This is CSV file
WITH ( FIELDTERMINATOR =',',rowterminator = '\n',FIRSTROW = 1 )
答案 0 :(得分:11)
好的,希望这一切都有帮助。我把您在评论中发布的内容转换为存储过程。方案是您有一个具有一致格式的平面文件,您每次都会将其加载到同一个表中(dbo.custCompInfo_Tab
)。该表将合并到dbo.Daily_Sync
上匹配的最终目标(CompanyName
)。我添加了一些数据列来进一步说明合并。
<强> SETUP:强>
CREATE TABLE dbo.Daily_Sync
(CompanyName VARCHAR(10)
, UserId INT
, col1 INT
, col2 INT
, col3 INT
)
CREATE TABLE dbo.custCompInfo_Tab
(CompanyName VARCHAR(10)
, col1 INT
, col2 INT
, col3 INT
)
我要加载两个数据文件,TrialBalance.txt和TrialBalance2.txt。它们包含以下数据:
TrialBalance.txt
abc,1,2,3
def,4,5,6
qwe,7,8,9
asd,10,11,12
zxc,13,14,15
TrialBalance2.txt
abc,1,2,3
def,20,21,22
qwe,7,8,9
xcv,10,11,12
xbv,13,14,15
我创建了一个截断登台表的存储过程,使用传入的文件路径中的数据加载表,然后将其合并到目标中。
CREATE PROCEDURE dbo.loadDailyData
@FullFilePath NVARCHAR(MAX)
AS
BEGIN
DECLARE @sql NVARCHAR(MAX)
TRUNCATE TABLE dbo.custCompInfo_Tab
SET @sql = N'BULK INSERT dbo.custCompInfo_Tab FROM ''' + @FullFilePath
+ ''' WITH ( FIELDTERMINATOR ='','',ROWTERMINATOR = ''\n'',FIRSTROW = 1 )'
SELECT @sql
EXEC sp_executesql @sql
MERGE INTO dbo.Daily_Sync AS TGT
USING
(SELECT CompanyName
, USER_ID() usrid
, col1
, col2
, col3
FROM dbo.custCompInfo_Tab
) AS SRC
ON TGT.Companyname = SRC.CompanyName
WHEN MATCHED
THEN UPDATE
SET TGT.Companyname = SRC.companyname
, TGT.col1 = SRC.col1
, TGT.col2 = SRC.col2
, TGT.col3 = SRC.col3
WHEN NOT MATCHED
THEN INSERT (companyname
, UserId
, col1
, col2
, col3
)
VALUES (SRC.CompanyName
, SRC.usrid
, SRC.col1
, SRC.col2
, SRC.col3
);
END
这里有动态sql用于构建字符串而不是行数,BULK INSERT
字符串就是返回的所有字符串。
最后,我们可以看到之前和之后的表格:
SELECT *
FROM dbo.custCompInfo_Tab
SELECT *
FROM dbo.Daily_Sync
EXEC dbo.loadDailyData @FullFilePath = 'D:\xmlData\TrialBalance.txt'
SELECT *
FROM dbo.custCompInfo_Tab
SELECT *
FROM dbo.Daily_Sync
EXEC dbo.loadDailyData @FullFilePath = 'D:\xmlData\TrialBalance2.txt'
SELECT *
FROM dbo.custCompInfo_Tab
SELECT *
FROM dbo.Daily_Sync
<强>结果:强>