2011-12-12 13 views
5

Tengo una tabla de base de datos, como a continuación:Cómo insertar de 20 millones de registro en la base de datos MySql lo más rápido posible

create table temperature 
(id int unsigned not null auto_increment primary key, 
temperature double 
); 

Y en mi programa tengo alrededor de 20 millones de temperatura para insertar en la tabla. Trabajo en entorno .Net, uso Connector/Net conectando a MySql. El código era el siguiente:

List<double> temps = new List<double>(); 
... 
string connStr = "server=localhost;user=name;database=test;port=3306;password=*****;"; 
MySqlConnection conn = new MySqlConnection(connStr); 
try 
{ 
    conn.Open(); 

    //temps.Count is about 20 million 
    for (int i = 0; i < temps.Count; i++) 
    { 
     string sql1 = "INSERT INTO temperature VALUES (null, "+temps[i]+")"; 
     MySqlCommand cmd1 = new MySqlCommand(sql1, conn); 
     cmd1.ExecuteNonQuery(); 
    } 

} 
catch (Exception ex) 
{ 
    Console.WriteLine(ex.ToString()); 
} 
conn.Close(); 

¿Cómo puedo insertar tantas líneas de datos lo más rápido posible? (Sólo se puede insertar 2000 registros cada minuto en mi ordenador.)

+1

Tengo curiosidad. ¿Por qué insertaría 20 millones de temperaturas en una base de datos? –

+0

¿Necesita autoincrement? Tengo una situación similar (en el servidor sql) y administro el lado del cliente de las teclas de incremento en el cargador. Manejo 75,000 filas por segundo en mi hardware actual. Sin SQL, sin embargo ... – TomTom

+0

También su sql "apesta";) ¿no puede enviar múltiples instrucciones de inserción en una sola ejecución? Es una cadena - ¿Puede manejar eso? 10 isnerts por viaje redondo es 10% de los viajes de ida y vuelta. Las roscas agregan más a eso (carga de múltiples roscas). – TomTom

Respuesta

5

puede utilizar el concepto de bulk insert que ejecuta muchas inserciones, al mismo tiempo, minimizar sobrecarga de llamar ExecuteNonQuery varias veces.

en MySQL esto se llama LOAD DATA, marque aquí para más detalles: http://dev.mysql.com/doc/refman/5.5/en/load-data.html

en MS SQL Server esto se llama bulk insert y es conocido como tal, por eso lo he mencionado con este nombre.

0

reglas generales: -

  1. use load data infile
  2. clave desactivar durante la importación, active de nuevo después de que todos los datos han sido importación
  3. ejecutar la secuencia de comandos en el propio servidor de base de datos, conectarse a través de socket en vez de TCP/ip

La mayoría de las sugerencias se explican en la documentación.

+0

regla general n. ° 2 no se aplicará aquí, ya que es clave primaria autonumber –

4

Hay varias formas de optimizar inserciones masivas. Algunos son:

  • LOAD DATA INFILE. Hay un wrapper API for .NET. Esta es la manera más rápida, pero tiene algunas limitaciones y diferencias semánticas a partir de inserciones simples.

  • múltiple fila INSERT declaraciones:

    INSERT INTO temperature (temperature) VALUES (1.0), (2.0), (3.0), ...

    No debe insertar 20.000.000 filas a la vez, pero puede tratar de 1,000 a 10,000 para una gran aceleración. Esta es una forma simple y sin problemas para aumentar la velocidad. Un factor de 10 y algunas veces mucho más a menudo es posible.

  • Bloqueando la tabla (LOCK TABLES).

  • Desactivando los índices temporalmente.

  • Afinación de opciones de MySQL.

  • INSERT DELAYED (muy probablemente no sea tan útil aquí).

La documentación le da more elaborate detail en las opciones. Algunas opciones dependen del tipo de tabla (InnoDB vs. MyISAM).

Una sugerencia general: especifique siempre las columnas que inserte delante de VALUES. Esto hace que el código sea más fácil de mantener.

Cuestiones relacionadas