使用 C 在 MySQL 数据库中插入数据速度缓慢

问题描述 投票:0回答:1

我的 MySQL 数据库中的数据插入速度很慢。我使用C语言插入数据,代码如下:

sprintf(szTemp, "cmd.exe /C mysql -u %s -p%s %s < %s", SZ_MYSQL_USER, SZ_MYSQL_MP, SZ_MYSQL_DATABASE, SZ_SQL_FILE);
system(szTemp);

最初,当数据库为空时,插入速度很快。然而,现在我的表step_data_result包含大约200万行,插入性能显着下降。

我尝试通过添加以下内容来修改插入和更新操作:

SET autocommit = 0;

-- My INSERT and UPDATE statements here

COMMIT;

然而,这并没有带来任何明显的改善。

我还执行了查询:

OPTIMIZE TABLE step_data_result;

这在当前会话中提供了暂时的性能改进,但系统重新启动后,插入缓慢的问题又出现了。

这是step_data_result的表结构:

CREATE TABLE IF NOT EXISTS `Lota`.`step_data_result` (
  `TIMESTAMP` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
  `ID` VARCHAR(38) NOT NULL DEFAULT '',
  `UUT_RESULT` VARCHAR(38) NOT NULL DEFAULT '',
  `STEP_PARENT` VARCHAR(38) NULL DEFAULT NULL,
  `STEP_NAME` VARCHAR(255) NULL DEFAULT NULL,
  `STEP_ID` VARCHAR(38) NOT NULL DEFAULT '',
  `STEP_TYPE` VARCHAR(255) NULL DEFAULT NULL,
  `STATUS` VARCHAR(255) NULL DEFAULT NULL,
  `REPORT_TEXT` TEXT NULL DEFAULT NULL,
  `DIAG` TEXT NULL DEFAULT NULL,
  `ERROR_OCCURRED` TINYINT(1) NOT NULL DEFAULT 0,
  `ERROR_CODE` INT(11) NULL DEFAULT NULL,
  `ERROR_MESSAGE` VARCHAR(1023) NULL DEFAULT NULL,
  `MODULE_TIME` FLOAT NULL DEFAULT NULL,
  `TOTAL_TIME` FLOAT NULL DEFAULT NULL,
  `NUM_LOOPS` INT(11) NULL DEFAULT NULL,
  `NUM_PASSED` INT(11) NULL DEFAULT NULL,
  `NUM_FAILED` INT(11) NULL DEFAULT NULL,
  `ENDING_LOOP_INDEX` INT(11) NULL DEFAULT NULL,
  `LOOP_INDEX` INT(11) NULL DEFAULT NULL,
  `INTERACTIVE_EXENUM` INT(11) NULL DEFAULT NULL,
  `STEP_GROUP` VARCHAR(30) NULL DEFAULT NULL,
  `STEP_INDEX` INT(11) NULL DEFAULT NULL,
  `ORDER_NUMBER` INT(11) NULL DEFAULT NULL,
  `VOLTAGE` DOUBLE NULL,
  PRIMARY KEY (`ID`),
  INDEX uut_result_step_parent (`STEP_PARENT`, `UUT_RESULT`)
) ENGINE = MyISAM
DEFAULT CHARACTER SET = latin1;

系统设置:

  • MySQL版本:5.5
  • 存储引擎:MyISAM
  • 内存:2GB
  • 数据大小:约200万行
  • 插入率:每次操作约 5,000 行

这是我的 MySQL 配置文件(my.ini):

[mysqld]
port=9102
basedir="C:/Program Files/MySQL/MySQL Server 5.5/"
datadir="C:/ProgramData/MySQL/MySQL Server 5.5/Data/"
character-set-server=latin1
default-storage-engine=MYISAM
sql-mode="STRICT_TRANS_TABLES,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
max_connections=100
table_cache=512
tmp_table_size=32M
max_heap_table_size=32M
thread_cache_size=16

# MyISAM Specific options
myisam_max_sort_file_size=100G
myisam_sort_buffer_size=64M
key_buffer_size=512M
bulk_insert_buffer_size=128M
read_buffer_size=512K
read_rnd_buffer_size=1M
sort_buffer_size=1M

# INNODB Specific options (not used)
innodb_data_home_dir="C:/Lota/Base_MySQL/"
skip-innodb

鉴于这些细节,您能否提供有关如何提高插入性能的建议,特别是考虑到重新启动后的速度减慢?谢谢!

sql mysql sql-insert myisam
1个回答
0
投票

A计划:

一次批量插入100-1000行。那是多行插入。

B计划:

将数据保存在 CSV 文件中并使用 LOAD DATA。 但如果数据尚未采用该格式,请务必在考虑此方法时考虑构建此类文件的成本。

C 计划:

如果 C 程序正在创建文件

SZ_SQL_FILE
,则将其通过管道传输到
mysql
。 这将避免写入磁盘并重新读取。

MyISAM 不知道有关

autocommit
COMMIT
的任何信息。

考虑切换到InnoDB;在很多情况下,它比 MyISAM 更快。 (我不知道这是否对您的情况有帮助。)

缩小数据类型;越小则速度越快。

INT
始终占用 4 个字节;还有更小的选择。
DOUBLE
占用8个字节;
FLOAT
(4 个字节)对于“电压”来说应该绰绰有余。

OPTIMIZE TABLE
很少有用。

向我们展示几行

SZ_SQL_FILE

© www.soinside.com 2019 - 2024. All rights reserved.