MySQL默认的数据提交操作模式是自动提交模式(autocommit)。这就表示除非显式地开始一个事务,否则每个查询都被当做一个单独的事务自动执行。我们可以通过设置autocommit的值改变是否是自动提交autocommit模式。查询当前数据库事务提交方式的命令为:

mysql> show variables like 'autocommit';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| autocommit | ON |
+---------------+-------+
1 row in set (0.04 sec)

其中“ON”代表autocommit模式为打开状态,使用MySQL C API关闭事务自动提交的代码为:

        MYSQL mysql;
mysql_init(&mysql);
if(!mysql_real_connect(&mysql, host, user, password, schema, port, NULL, 0))
{
printf("MySQL数据库连接失败。\n");
return -1;
}
int set_cs_r = mysql_set_character_set(&mysql, "gbk");
mysql_autocommit(&mysql, 0);

  MySQL默认的存储引擎是MyISAM,MyISAM存储引擎不支持事务处理,所以改变autocommit没有什么作用,InnoDB存储引擎支持事务处理。InnoDB表引擎下关闭mysql自动事务提交可以大大提高数据插入的效率,这是因为如果需要插入1000条数据,mysql会自动发起(提交)1000次的数据写入请求,如果把autocommit关闭掉,通过程序来控制,只要一次commit就可以搞定。示例代码(逻辑过程)如下:

int H_Utility::insertRecordsToMySQL(
const char* dataFilePath,
const char* host,
const char* user,
const char* password,
const char* schema,
const char* table,
const int port,
const char* logFilePath)
{
ifstream rpf;
rpf.open(dataFilePath);
int lineCount = 0;
if (rpf.is_open())
{
MYSQL mysql;
mysql_init(&mysql);
if(!mysql_real_connect(&mysql, host, user, password, schema, port, NULL, 0))
{
printf("MySQL数据库连接失败。\n");
return -1;
}
ofstream f1(logFilePath);
if (!f1.is_open())
{
printf("日志文件创建失败!\n");
return 0;
}
mysql_autocommit(&mysql, 0);//关闭自动提交
char* out_text = new char[1024];
int cursor = 0;
while (!rpf.eof())
{
memset(out_text,0x00,1024);
rpf.getline(out_text,1024);
string str(out_text);
if (str.length()>0)
{
lineCount++;
if (lineCount>1)
{
std::vector<string> strVec;
int cellCount = H_Utility::stringSplitToVector(str.c_str(), strVec, ",");
if (cellCount<3)
{
printf("第%d行数据不完整,写入失败:\n",lineCount);
f1<<str<<endl;
continue;
}
string sql_str = "";
sql_str.append("INSERT INTO `").append(SCHEMA_NAME).append("`.`").append(TABLE_NAME).append("` ");
sql_str.append("(id,name,birthday) values (");
sql_str.append(strVec[0]).append(",'").append(strVec[1]).append("',");
sql_str.append("STR_TO_DATE('").append(strVec[31]).append("','%Y-%m-%d %H:%i:%s'))");
int iSuccess = mysql_query(&mysql, sql_str.c_str());
if (iSuccess != 0)
{
const char *mysql_err = mysql_error(&mysql);
printf("%s\n",mysql_err);
f1<<str<<endl;
}
else
{
cursor++;
}
if (cursor==50000)//每50000条记录提交一次
{
mysql_commit(&mysql);
cursor = 0;
printf("%d\n",lineCount);
}
}
}
}
delete []out_text;
rpf.close();
f1.flush();
f1.close();
mysql_close(&mysql);
}
return lineCount;
}

  在本人笔记本电脑上(Thinkpad T430; i5-3380 CPU; 4G DDR3 RAM; 500G&7200RPM HDD; Win7 旗舰版 x64; MySQL 5.6 社区版)的测试结果为:上述代码往mysql中插入200万条记录(数据文件大小约为300M)耗时仅约为345秒,而逐条提交时运行约3小时仅仅写入了 不到50万条数据,由此可见在使用InnoDB数据引擎进行大数据量插入时,代码中必须对该问题进行优化。

C API向MySQL插入批量数据的快速方法——关于mysql_autocommit的更多相关文章

  1. mysql 插入/更新数据

    mysql 插入/更新数据 INSERT 语句 1.一次性列出全部字段的值,例如: INSERT INTO student VALUES('Chenqi','M', 29); INSERT INTO ...

  2. [转载]mysql插入大量数据

    mysql的批量数据格式, 比如 INSERT INTO TABLES (LABLE1,LABLE2,LABLE3,...)  VALUES(NUM11,NUM12,NUM13,...),  (NUM ...

  3. MySQL插入中文数据出现?号

    原文转载自:https://blog.csdn.net/LynneZoe/article/details/79174119 运行环境:win10 mysql版本:Mysql5.6 做一个项目的时候,向 ...

  4. mysql插入中文数据变成问号怎么处理

    插入中文数据变成问号,一般都是因为字符集没有设置成utf8的原因 1.修改字符集: ALTER TABLE 表名 MODIFY 列名 类型(50) CHARACTER SET "utf8&q ...

  5. laravel 解决mysql插入相同数据的问题

    1.背景: 每天0点定时任务统计数据,实现目标是统计时如果没有今天的统计数据,那就执行insert操作 如果存在那就执行update操作: 代码逻辑 1 if(报表存在){ 2 update(); 3 ...

  6. C API 连接MySQL及批量插入

    CMySQLMgr.h: #ifndef _CMYSQLMGR_H_ #define _CMYSQLMGR_H_ #include <iostream> #include "my ...

  7. 【MySQL】批量数据循环插入

    双重循环插入 DELIMITER ;; CREATE PROCEDURE test_insert() BEGIN ; ; ) DO -- repeat ; -- select a; ) DO ); ; ...

  8. MySQL插入大量数据探讨

    笔者想进行数据库查询优化探索,但是前提是需要一个很大的表,因此得先导入大量数据至一张表中. 准备工作 准备一张表,id为主键且自增: 方案一 首先我想到的方案就是通过for循环插入 xml文件: &l ...

  9. SQL Server 2012中快速插入批量数据的示例及疑惑

    SQL Server 2008中SQL应用系列--目录索引 今天在做一个案例演示时,在SQL Server 2012中使用Insert语句插入1万条数据,结果遇到了一个奇怪的现象,现将过程分享出来,以 ...

随机推荐

  1. Motion——shake攻略

    1.子类化窗口 如果响应链中没有motionEnded:withEvent:消息的接收者,那么该消息就会被发送给应用程序的window对象.所以需要在window对象上拦截motionEnded:wi ...

  2. MSDN无法显示该页的解决办法

    今天打开msdn,发现 查阅api时候 出现 “无法显示该页的解决办法“ 这个问题.解决方案如下: 在“运行”中输入regsvr32 "C:\Program Files\Common Fil ...

  3. Java基础知识强化之集合框架笔记53:Map集合之Map集合的遍历 键值对对象找键和值

    1. Map集合的遍历(键值对对象找键和值) Map -- 夫妻对  思路:  A: 获取所有结婚证的集合  B: 遍历结婚证的集合,得到每一个结婚证  C: 根据结婚证获取丈夫和妻子 转换:  A: ...

  4. Audit(查看审核/审计信息)

    2013需要到 网站集管理-网站集审核设置 中设置要开启的审核项,开启之后sharepoint才会记录信息,信息存储在contentDB的AuditData中: 去读审计信息的sharepoint代码 ...

  5. Google Map API v2 番外篇 关于gps位置偏差及修正方法探讨

    我的手机是M35C,在我自己的map activity中,通过gps获取到的经纬度比实际地址总是有500米左右的偏差. 在网上搜索了很多,都说这个是测绘局为了保密故意弄成这样的.gps全球定位系统获得 ...

  6. MegaCli监控RAID磁盘健康信息

    首先有必要先介绍一下有关RAID卡的使用,有关Cache问题也有个人理解:生产系统上的物理机磁盘配置大多都是RAID5,之前会经常性的遇到磁盘IO在某个时间极度的跟不上节奏,稍微写入量,磁盘utils ...

  7. linux 上不去网

    linux 上不去网   ip dns无误 ping可以到达网关 可能原因 网卡睡眠 ethtool eht0  //查看eht0网口基本设置 mii-tool -w eth0

  8. Android 5.0 新特性

    Material Design Material Design简介 Material Design是谷歌新的设计语言,谷歌希望寄由此来统一各种平台上的用户体验,Material Design的特点是干 ...

  9. android检查自动升级

    好像大半年没发点啥了,也不知道自己瞎忙啥,闲下来发给最近的东东<安卓在线升级> 类已经封装好了,简单的调用就OK了.这里的数据交互,我是用.NET写的一个webservice来交互.废话也 ...

  10. css3遇到的一些属性

    rgba          是由red.green.blue 三种颜色搭配出来的box-shadow     向元素添加阴影层,水平阴影位置,垂直阴影位置,后面是可选:模糊距离,阴影大小,颜色,是否是 ...