简体   繁体   English

创建与csv中具有相同列的表

[英]Creating table with the same columns as in a csv

I am writing a stored procedure which is supposed to take data from a csv file and insert into a table . 我正在编写一个stored procedure ,该过程应该从csv文件中获取数据并inserttable My problem is that the number of columns in the csv file are not fixed(ie number of columns is variable). 我的问题是,数量columnscsv文件中没有固定的(即数columns是可变的)。 So I need some way to create a temporary table with exactly the same number of columns as in the csv file. 因此,我需要某种方式来创建一个temporary table ,该tablecolumns数与csv文件中的columns数完全相同。 So that I can use bulk insert . 这样我就可以使用bulk insert

improved nadeems script... A little bit more robust. 改进的nadeems脚本...更加强大。

This code is excelent for loading multiple CSV files without using the default wizzards. 此代码非常适合在不使用默认向导的情况下加载多个CSV文件的情况。

SET ANSI_NULLS ON
GO

SET QUOTED_IDENTIFIER ON
GO


CREATE proc [dbo].[importeer_csv_as_table]
@path nvarchar(255),
@new_table_name varchar(255), 
@field_terminator varchar(255),
@row_terminator varchar(255)
as
begin
declare @execsql nvarchar(max)
declare @tempstr varchar(max)
declare @col varchar(max)
declare @table nvarchar(max)
declare @drop_table varchar(max)


-- Create a temp table to with one column to hold the first row of the csv file

  create table #tbl (line varchar(1000))
   set @execsql = 
        'bulk insert #tbl  
        from ''' + @path + '''  
        with (  
                 fieldterminator =''' + @row_terminator + ''',
                 firstrow = 1,  
                 rowterminator = ''' + @row_terminator + ''',
                 lastrow = 1 
              )         
       ' 

   exec sp_executesql @stmt=@execsql 


   --replace field terminator with comma
   update #tbl set line = replace(line, @field_terminator, ',')

   set @col = ''
   set @tempstr = (select top 1 rtrim(replace(line, char(9), ',')) from #tbl)
   drop table #tbl
   while charindex(',',@tempstr) > 0
    begin           

       set @col=@col + '[' + ltrim(rtrim(substring(@tempstr, 1, charindex(',',@tempstr)-1))) + '] varchar(max),'     

       set @tempstr = substring(@tempstr, charindex(',',@tempstr)+1, len(@tempstr)) 
    end
    set @col = @col + '[' + @tempstr + '] varchar(max)'

   if object_id(@new_table_name) is not null
   begin
      set @drop_table = 'drop table [' + @new_table_name + ']'

      exec sp_executesql @stmt= @drop_table
   end 

   set @table = 'create table [' + @new_table_name + '] (' + @col + ')'

   --select @table


   exec sp_executesql @stmt=@table

   --Load data from csvle
   set @execsql = 
        'bulk insert [' + @new_table_name + ']
        from ''' + @path + '''  
        with (  
                 fieldterminator =''' + @field_terminator + ''',
                 firstrow = 2,  
                 rowterminator = ''' + @row_terminator + '''              
              )         
       '  

   exec sp_executesql @stmt=@execsql 

end

GO

You could use Powershell to process the CSV file, there is an example here which you could probably adapt to take account of the variable number of fields. 你可以使用PowerShell的处理CSV文件中,有一个例子在这里 ,你也许可以适应考虑场的数目可变的。 You can build the SQL to create a table and then issue a bulk load. 您可以构建SQL来创建表,然后发出批量加载。

Well I tried solving the issue by writing a sp which will take the csv file path as parameter and create a table names as temptable with the same format as that of the number of columns in the csv. 好吧,我尝试通过编写sp来解决该问题,该sp将以csv文件路径作为参数并以temptable的形式创建表名称,格式与csv中的列数格式相同。 CSV file looks like CSV档案看起来像

eid,ename,esalary,etemp
1,Mark,1000,
2,Peter,1000,

Stored Proc script 存储的Proc脚本

create proc createtable
@path nvarchar(50)
as
begin
declare @execSQL nvarchar(1000)
declare @tempstr varchar(1000)
declare @col varchar(1000)
declare @table nvarchar(1000)

-- Create a temp table to with one column to hold the first row of the csv file

  CREATE TABLE #tbl (line VARCHAR(1000))
   SET @execSQL = 
        'BULK INSERT #tbl  
        FROM ''' + @path + '''  
        WITH (  
                 FIELDTERMINATOR =''\n'',
                 FIRSTROW = 1,  
                 ROWTERMINATOR = ''\n'',
                 LASTROW = 1 
              )         
       ' 

   EXEC sp_executesql @stmt=@execSQL 

   SET @col = ''
   SET @tempstr = (SELECT TOP 1 RTRIM(REPLACE(Line, CHAR(9), ',')) FROM #tbl)
   DROP TABLE #tbl
   WHILE CHARINDEX(',',@tempstr) > 0
    BEGIN           

       SET @col=@col + LTRIM(RTRIM(SUBSTRING(@tempstr, 1, CHARINDEX(',',@tempstr)-1))) + ' varchar(100),'     

       SET @tempstr = SUBSTRING(@tempstr, CHARINDEX(',',@tempstr)+1, len(@tempstr)) 
    END
    SET @col = @col + @tempstr + ' varchar(100)'

   if object_id('temptable') is not null
   drop table temptable

   SET @table = 'create table temptable (' + @col + ')'

   EXEC sp_executesql @stmt=@table

-- Load data from csv
   SET @execSQL = 
        'BULK INSERT temptable
        FROM ''' + @path + '''  
        WITH (  
                 FIELDTERMINATOR ='','',
                 FIRSTROW = 2,  
                 ROWTERMINATOR = ''\n''              
              )         
       '  

   EXEC sp_executesql @stmt=@execSQL 

end

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

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