Dans ma candidature, mes INSERT semblent prendre une grande partie du temps. J'ai un grand nombre d'objets en mémoire (~ 40-50 000) que je souhaite insérer dans une table.
Prenons un exemple de table
CREATE TABLE bill (
id BIGINT(20) PRIMARY KEY,
amount INT(11) DEFAULT 0,
bill_date DATETIME DEFAULT NOW(),
INDEX (bill_date)
) ENGINE=InnoDB
En prenant 3 lignes comme taille de lot, voici les approches auxquelles je pourrais penser pour insérer
Approche 1 - construire et cuire 3 inserts bruts
INSERT INTO bill (amount, bill_date) VALUES (10, '2012-01-01 00:00:00');
INSERT INTO bill (amount, bill_date) VALUES (20, '2012-01-02 00:00:00');
INSERT INTO bill (amount, bill_date) VALUES (40, '2013-02-05 00:00:00');
Approche 2 - regrouper les valeurs en 1 requête
INSERT INTO bill (amount, bill_date) VALUES
(10, '2012-01-01 00:00:00'),
(20, '2012-01-02 00:00:00'),
(40, '2013-02-05 00:00:00');
Approche 3 - lancer cette requête 1 fois en passant 6 paramètres
INSERT INTO bill (amount, bill_date) VALUES
(?, ?), (?, ?), (?, ?);
Approche 4 - Lancer cette requête préparée 3 fois en changeant les 2 paramètres à chaque fois
INSERT INTO bill (amount, bill_date) VALUES (?, ?);
Toute autre approche est la bienvenue.
Ma question est
Quelle est la façon la plus rapide de créer plusieurs insertions dans une table?
J'ai lu ce lien sur la vitesse d'insertion mysql et ce guide de programmation JDBC , mais je ne suis pas en mesure de conclure.
Mon cas -
Actuellement, ma table a environ 20 colonnes, dont la plupart sont des nombres, avec quelques varchar (60) et 1 colonne de texte. Mysql version 5.5. Fonctionnant sur INNODB et possède 1 index sur les clés primaires entières. Toutes les requêtes s'exécutent en transaction.
Je construis mes requêtes à partir de Java et j'utilise Spring JDBC pour exécuter les requêtes.
Je suis actuellement en train de suivre l'approche 3, cela prend environ 10 secondes pour 20 000 insertions dans une table vide, sans compter le temps nécessaire pour construire la requête.
Pour garder les choses en perspective, il faut 100 à 200 millis pour récupérer les données de la table.
Y a-t-il quelque chose qui me manque? Comment accélérer les inserts?