zoukankan      html  css  js  c++  java
  • BCP

    转:(总结) SQL Server Bulk Insert 批量数据导入          

    SQL Server的Bulk Insert语句可以将本地或远程的数据文件批量导入到数据库中,速度非常的快。远程文件必须共享才行,文件路径须使用通用约定(UNC)名称,即"\\服务器名或IP\共享名\路径\文件名"的形式。

    * 1. 由于Bulk Insert通常配合格式化文件批量导入数据更方便,所以这里先介绍bcp工具导出格式化文件的方法。

    bcp是SQL Server提供的命令行实用工具提供了数据的导出、导入、格式文件导出等功能,导出格式化文件的语法如下:

    Sql代码 复制代码 收藏代码
    1. bcp 数据库名.用户名.表名 format nul -- 这里的nul必须存在,用于不是导出和导入数据的情况下  
    2. -f 输出的格式化文件名 [-x] -c  -- -x参数指定输出的格式文件为xml格式(默认非xml格式); -c参数指定数据存储方式为字符,并默认指定'\t'作为字段间隔符;'\n'作为行间隔符  
    3. [-t 字段间隔符] [-r 行间隔符号]  -- -t与-r参数可选,用于覆盖-c指定的默认间隔符  
    4. -T -- 指定数据库连接可信,即使用Windows身份登录  
    bcp 数据库名.用户名.表名 format nul -- 这里的nul必须存在,用于不是导出和导入数据的情况下
    -f 输出的格式化文件名 [-x] -c  -- -x参数指定输出的格式文件为xml格式(默认非xml格式); -c参数指定数据存储方式为字符,并默认指定'\t'作为字段间隔符;'\n'作为行间隔符
    [-t 字段间隔符] [-r 行间隔符号]  -- -t与-r参数可选,用于覆盖-c指定的默认间隔符
    -T -- 指定数据库连接可信,即使用Windows身份登录

    * 2. Bulk Insert

     根据格式文件导入数据文件,语法格式如下:

    Sql代码 复制代码 收藏代码
    1. Bulk insert 数据库名.用户名.表名  
    2. from '数据文件路径'  
    3. with  
    4. (  
    5. formatfile = '格式文件路径',  
    6. FirstRow = 2    --指定数据文件中开始的行数,默认是1  
    7. )  
    Bulk insert 数据库名.用户名.表名
    from '数据文件路径'
    with
    (
    formatfile = '格式文件路径',
    FirstRow = 2	--指定数据文件中开始的行数,默认是1
    )

    * 3. OPENRORWSET(BULK)函数

    有时,使用OPENROWSET(BULK)函数可以更灵活地选取想要的字段插入到原表或者其他表中,其语法格式为:

    Sql代码 复制代码 收藏代码
    1. INSERT INTO to_table_name SELECT filed_name_list  
    2. FROM OPENROWSET(BULK N'path_to_data_file', FORMATFILE=N'path_to_format_file'AS new_table_name  
     INSERT INTO to_table_name SELECT filed_name_list
     FROM OPENROWSET(BULK N'path_to_data_file', FORMATFILE=N'path_to_format_file') AS new_table_name
      

     当然,该函数也可以这么使用:

    Sql代码 复制代码 收藏代码
    1. SELECT field_name_list INTO temp_table_name  
    2. FROM OPENROWSET(BULK N'path_to_data_file', FORMATFILE=N'path_to_format_file'AS new_table_name  
    SELECT field_name_list INTO temp_table_name
    FROM OPENROWSET(BULK N'path_to_data_file', FORMATFILE=N'path_to_format_file') AS new_table_name
     

    下面举一个完整的例子:

    1)创建数据库、表并填充测试数据,脚本如下:

    Sql代码 复制代码 收藏代码
    1. -- 创建数据库  
    2. CREATE DATABASE [db_mgr]  
    3. GO  
    4. --创建测试表  
    5. USE db_mgr  
    6. CREATE TABLE dbo.T_Student(  
    7.     F_ID [int] IDENTITY(1,1) NOT NULL,  
    8.     F_Code varchar(10) ,  
    9.     F_Name varchar(100) ,  
    10.     F_Memo nvarchar(500) ,  
    11.     F_Memo2 ntext ,  
    12.     PRIMARY KEY  (F_ID)  
    13. )   
    14. GO  
    15.   
    16. --填充测试数据  
    17. Insert Into T_Student(F_Code, F_Name, F_Memo, F_Memo2) select  
    18. 'code001''name001''memo001''备注001' union all select  
    19. 'code002''name002''memo002''备注002' union all select  
    20. 'code003''name003''memo003''备注003' union all select  
    21. 'code004''name004''memo004''备注004' union all select  
    22. 'code005''name005''memo005''备注005' union all select  
    23. 'code006''name006''memo006''备注006'  
    -- 创建数据库
    CREATE DATABASE [db_mgr]
    GO
    --创建测试表
    USE db_mgr
    CREATE TABLE dbo.T_Student(
    	F_ID [int] IDENTITY(1,1) NOT NULL,
    	F_Code varchar(10) ,
    	F_Name varchar(100) ,
    	F_Memo nvarchar(500) ,
    	F_Memo2 ntext ,
    	PRIMARY KEY  (F_ID)
    ) 
    GO
    
    --填充测试数据
    Insert Into T_Student(F_Code, F_Name, F_Memo, F_Memo2) select
    'code001', 'name001', 'memo001', '备注001' union all select
    'code002', 'name002', 'memo002', '备注002' union all select
    'code003', 'name003', 'memo003', '备注003' union all select
    'code004', 'name004', 'memo004', '备注004' union all select
    'code005', 'name005', 'memo005', '备注005' union all select
    'code006', 'name006', 'memo006', '备注006'

     2)我们可以使用SQL Server的master..xp_cmdshell存储过程将CMD的命令传给系统,这样就可以直接在SQL Server的查询处理器中直接输入bcp的命令,而不用切换到命令模式下执行。SQL Server 出于安全目的默认将该存储过程禁用了,开启方法如下:

    Sql代码 复制代码 收藏代码
    1. --开启xp_cmdshell存储过程(开启后有安全隐患)  
    2. EXEC sp_configure 'show advanced options', 1;  
    3. RECONFIGURE;EXEC sp_configure 'xp_cmdshell', 1;  
    4. EXEC sp_configure 'show advanced options', 0;  
    5. RECONFIGURE;  
    --开启xp_cmdshell存储过程(开启后有安全隐患)
    EXEC sp_configure 'show advanced options', 1;
    RECONFIGURE;EXEC sp_configure 'xp_cmdshell', 1;
    EXEC sp_configure 'show advanced options', 0;
    RECONFIGURE;

    3)使用bcp导出格式文件:

    Sql代码 复制代码 收藏代码
    1. EXEC master..xp_cmdshell 'BCP db_mgr.dbo.T_Student format nul -f C:/student_fmt.xml -x -c -T'  
    EXEC master..xp_cmdshell 'BCP db_mgr.dbo.T_Student format nul -f C:/student_fmt.xml -x -c -T'

    4)使用bcp导出数据文件:

    Sql代码 复制代码 收藏代码
    1. EXEC master..xp_cmdshell 'BCP db_mgr.dbo.T_Student out C:/student.data -f C:/student_fmt.xml -T'  
    2. truncate table db_mgr.dbo.T_Student -- 将表中数据清空  
    EXEC master..xp_cmdshell 'BCP db_mgr.dbo.T_Student out C:/student.data -f C:/student_fmt.xml -T'
    truncate table db_mgr.dbo.T_Student -- 将表中数据清空

      注意:在实际使用过程中,数据文件可以由程序生成,如日志记录等!

    5)使用Bulk Insert语句批量导入数据文件:

    Sql代码 复制代码 收藏代码
    1. BULK INSERT db_mgr.dbo.T_Student  
    2. FROM 'C:/student.data'  
    3. WITH  
    4. (  
    5.     FORMATFILE = 'C:/student_fmt.xml'  
    6. )  
    BULK INSERT db_mgr.dbo.T_Student
    FROM 'C:/student.data'
    WITH
    (
    	FORMATFILE = 'C:/student_fmt.xml'
    )

    6)使用OPENROWSET(BULK)的例子:

    Sql代码 复制代码 收藏代码
    1. INSERT INTO db_mgr.dbo.T_Student(F_Code, F_Name) SELECT F_Code, F_Name  
    2. FROM OPENROWSET(BULK N'C:/student_c.data', FORMATFILE=N'C:/student_fmt_c.xml'AS new_table_name -- T_Student表必须已存在  
    3.   
    4. SELECT F_Code, F_Name INTO db_mgr.dbo.tt  
    5. FROM OPENROWSET(BULK N'C:/student_c.data', FORMATFILE=N'C:/student_fmt_c.xml'AS new_table_name -- tt表可以不存在  
    INSERT INTO db_mgr.dbo.T_Student(F_Code, F_Name) SELECT F_Code, F_Name
    FROM OPENROWSET(BULK N'C:/student_c.data', FORMATFILE=N'C:/student_fmt_c.xml') AS new_table_name -- T_Student表必须已存在
    
    SELECT F_Code, F_Name INTO db_mgr.dbo.tt
    FROM OPENROWSET(BULK N'C:/student_c.data', FORMATFILE=N'C:/student_fmt_c.xml') AS new_table_name -- tt表可以不存在

    参考:

    使用 BULK INSERT 或 OPENROWSET(BULK...) 导入大容量数据(尤其是关于安全的那部分,导入远程文件时应特别注意):

    http://msdn.microsoft.com/zh-cn/library/ms175915.aspx

    创建格式化文件:

    http://msdn.microsoft.com/zh-cn/library/ms191516.aspx

    OPENROWSET (Transact-SQL):

    http://msdn.microsoft.com/zh-cn/library/ms190312.aspx

    BULK INSERT (Transact-SQL):

    http://msdn.microsoft.com/zh-cn/library/ms188365.aspx

    bcp 实用工具:

    http://msdn.microsoft.com/zh-cn/library/ms162802.aspx

  • 相关阅读:
    inner join 与 left join 之间的区别
    从group by 展开去
    distinct的用法
    with as的用法
    substr函数的用法
    Oracle的dual表是个什么东东
    Sql函数笔记一、case when
    在本地没有安装Oracle的情况下,使用plsql远程连接数据库
    【Ubuntu】执行定时任务(cron)
    【系统】Ubuntu和win7双系统更改系统引导菜单
  • 原文地址:https://www.cnblogs.com/lingdanglfw/p/3647307.html
Copyright © 2011-2022 走看看