MySQL 请求的事务和缓冲列表
MySQL transaction and buffered list of requests
我有一个 C++ 代码可以解析文件并根据这些文件的内容更新 MySQL 数据库。
我 运行 我的代码在 Windows 10,MySQL 5.7,我的基础使用 InnoDB 引擎。 MySQL 调用是通过我自己的 libmysql 包装器执行的。
为了优化此代码,我将更新请求追加到缓冲区中,直到达到缓冲区的最大大小,然后同时发送整个缓冲区(包含 N 个更新)。整个过程在单个事务中完成。
我的代码如下所示:
MySQLWrapper.StartTransaction();
string QueryBuffer = "";
// Element count is the number of elements parsed from the files
for( int i = 0 ; i < ElementCount ; ++i )
{
bool FlushBuffer =
( i> 0 && ! (( i + 1 ) % N) ) ||
( i == ElementCount - 1 ); // determines if we have reached the buffer max number of requests
QueryBuffer += "INSERT INTO mytable (myfield) VALUES (" Element[ i ] ");";
if( FlushBuffer )
{
MySQLWrapper.SendRequest( QueryBuffer );
QueryBuffer.assign("");
}
}
MySQLWrapper.Commit();
SendRequest(string Request) 的实现基本上是:
void SendRequest(string Request)
{
mysql_query( SQLSocket, Request.c_str())
}
但是在提交事务的时候,恰好事务已经中断:MySQL表示committing状态不正确。我试过做同样的事情,但是一个一个地发送请求,并且在提交时没有发生这个错误。
那么,我的两个问题是:
- 您知道为什么一次发送多个请求会中断我的交易吗?
- 您认为使用缓冲请求列表真的可以优化我的代码吗?
创建一个包含多个值的 INSERT,而不是多个 INSERT。 IOW,在循环之前,
有 INSERT INTO TABLE (columns)
,然后在循环内,为每个值集附加 (values),
。
MySQLWrapper.StartTransaction();
string QueryBuffer = "INSERT INTO mytable (myfield) VALUES ";
// Element count is the number of elements parsed from the files
for( int i = 0 ; i < ElementCount ; ++i )
{
bool FlushBuffer =
( i> 0 && ! (( i + 1 ) % N) ) ||
( i == ElementCount - 1 ); // determines if we have reached the buffer max number of requests
QueryBuffer += "(" Element[ i ] ")";
if( flushbuffer ) {
QueryBuffer += ";";
} else {
QueryBuffer += ",";
}
if( FlushBuffer )
{
MySQLWrapper.SendRequest( QueryBuffer );
QueryBuffer.assign("");
}
}
MySQLWrapper.Commit();
生成的 SQL 语句类似于:
INSERT INTO mytable
(myfield)
VALUES
(1),
(2),
(3),
(3);
我有一个 C++ 代码可以解析文件并根据这些文件的内容更新 MySQL 数据库。 我 运行 我的代码在 Windows 10,MySQL 5.7,我的基础使用 InnoDB 引擎。 MySQL 调用是通过我自己的 libmysql 包装器执行的。
为了优化此代码,我将更新请求追加到缓冲区中,直到达到缓冲区的最大大小,然后同时发送整个缓冲区(包含 N 个更新)。整个过程在单个事务中完成。
我的代码如下所示:
MySQLWrapper.StartTransaction();
string QueryBuffer = "";
// Element count is the number of elements parsed from the files
for( int i = 0 ; i < ElementCount ; ++i )
{
bool FlushBuffer =
( i> 0 && ! (( i + 1 ) % N) ) ||
( i == ElementCount - 1 ); // determines if we have reached the buffer max number of requests
QueryBuffer += "INSERT INTO mytable (myfield) VALUES (" Element[ i ] ");";
if( FlushBuffer )
{
MySQLWrapper.SendRequest( QueryBuffer );
QueryBuffer.assign("");
}
}
MySQLWrapper.Commit();
SendRequest(string Request) 的实现基本上是:
void SendRequest(string Request)
{
mysql_query( SQLSocket, Request.c_str())
}
但是在提交事务的时候,恰好事务已经中断:MySQL表示committing状态不正确。我试过做同样的事情,但是一个一个地发送请求,并且在提交时没有发生这个错误。
那么,我的两个问题是:
- 您知道为什么一次发送多个请求会中断我的交易吗?
- 您认为使用缓冲请求列表真的可以优化我的代码吗?
创建一个包含多个值的 INSERT,而不是多个 INSERT。 IOW,在循环之前,
有 INSERT INTO TABLE (columns)
,然后在循环内,为每个值集附加 (values),
。
MySQLWrapper.StartTransaction();
string QueryBuffer = "INSERT INTO mytable (myfield) VALUES ";
// Element count is the number of elements parsed from the files
for( int i = 0 ; i < ElementCount ; ++i )
{
bool FlushBuffer =
( i> 0 && ! (( i + 1 ) % N) ) ||
( i == ElementCount - 1 ); // determines if we have reached the buffer max number of requests
QueryBuffer += "(" Element[ i ] ")";
if( flushbuffer ) {
QueryBuffer += ";";
} else {
QueryBuffer += ",";
}
if( FlushBuffer )
{
MySQLWrapper.SendRequest( QueryBuffer );
QueryBuffer.assign("");
}
}
MySQLWrapper.Commit();
生成的 SQL 语句类似于:
INSERT INTO mytable
(myfield)
VALUES
(1),
(2),
(3),
(3);