在C#中将100 000条记录插入MDB文件的最快方法是什么?

我知道这些问题相当普遍,但我整天都在搜索,但我找不到合适的方法。

这是我的代码,使用C#将大约100 000个虚拟记录插入到MDB文件中。

OleDbConnection con = new OleDbConnection(); string dbProvider = "PROVIDER=Microsoft.Jet.OLEDB.4.0;"; string dbSource = "Data Source = D:/programming/sample.mdb"; con.ConnectionString = dbProvider + dbSource; OleDbCommand cmd = new OleDbCommand(); cmd.Connection = con; cmd.CommandText = "INSERT INTO tblBooks (Title, Price, Tag, Author) VALUES (@title, @price, @tag, @author)"; cmd.Parameters.AddWithValue("@title", "Dummy Text 1"); cmd.Parameters.AddWithValue("@price", 10); cmd.Parameters.AddWithValue("@tag", "Dummy Text 2"); cmd.Parameters.AddWithValue("@author", "Dummy Text 3"); con.Open(); for (int i = 0; i < 100000; i++) { cmd.ExecuteNonQuery(); } con.Close(); 

此代码大约需要一分钟才能运行。 这是正常的吗? 更快地做到这一点的正确方法是什么?

如果您碰巧已经有一个“数字表”(至少有100,000行),那么Remou的答案几乎肯定会让工作完成得最快。 我在VBA和查询中尝试了快速测试

 Dim t0 As Single t0 = Timer CurrentDb.Execute _ "INSERT INTO tblBooks (Title, Price, Tag, Author) " & _ "SELECT 'Dummy Text 1', 10, 'Dummy Text 2', 'Dummy Text 3' FROM Numbers", _ dbFailOnError Debug.Print Format(Timer - t0, "0.0") & " seconds" 

在不到2秒的时间内创建了100,000行。

但是,如果您还没有数字表,那么您需要首先创建该表,因此如果这是一次性要求,那么您可能最好只是优化代码。

您的问题中发布的代码在我的计算机上花了45秒。 两项显着缩短执行时间的增强function包括:

  1. 使用.Prepare() :单独将经过的时间减少到16秒

  2. 使用OleDbTransaction :在事务中包装插入(除了使用.Prepare() )还将经过的时间减少到10秒。

修改后的代码如下所示:

 var sw = new System.Diagnostics.Stopwatch(); sw.Start(); OleDbConnection con = new OleDbConnection(); string dbProvider = "PROVIDER=Microsoft.Jet.OLEDB.4.0;"; string dbSource = "Data Source = C:/Users/Gord/Desktop/speed.mdb"; con.ConnectionString = dbProvider + dbSource; con.Open(); OleDbCommand cmd = new OleDbCommand(); cmd.Connection = con; cmd.CommandText = "INSERT INTO tblBooks (Title, Price, Tag, Author) VALUES (?,?,?,?)"; cmd.Parameters.Add("?", OleDbType.VarWChar, 255); cmd.Parameters.Add("?", OleDbType.Currency); cmd.Parameters.Add("?", OleDbType.VarWChar, 255); cmd.Parameters.Add("?", OleDbType.VarWChar, 255); cmd.Prepare(); cmd.Parameters[0].Value = "Dummy Text 1"; cmd.Parameters[1].Value = 10; cmd.Parameters[2].Value = "Dummy Text 2"; cmd.Parameters[3].Value = "Dummy Text 3"; OleDbTransaction trn = con.BeginTransaction(); cmd.Transaction = trn; for (int i = 0; i < 100000; i++) { cmd.ExecuteNonQuery(); } trn.Commit(); con.Close(); sw.Stop(); Console.WriteLine(String.Format("{0:0.0} seconds", sw.ElapsedMilliseconds / 1000.0)); 

(奖金回答:)

如果有人想知道OleDbDataAdapter是否可以更快地插入行,似乎没有。 以下代码确实创建了100,000条记录……

 var da = new OleDbDataAdapter("SELECT [ID], [Title], [Price], [Tag], [Author] FROM [tblBooks] WHERE False", con); var cb = new OleDbCommandBuilder(da); cb.QuotePrefix = "["; cb.QuoteSuffix = "]"; var dt = new System.Data.DataTable(); da.Fill(dt); for (int i = 0; i < 100000; i++) { System.Data.DataRow dr = dt.NewRow(); dr["Title"] = "Dummy Text 1"; dr["Price"] = 10; dr["Tag"] = "Dummy Text 2"; dr["Author"] = "Dummy Text 3"; dt.Rows.Add(dr); } da.Update(dt); 

...但运行时间比问题中的原始代码长约30%。

您可以使用数字表添加多个相同的行,例如:

 INSERT INTO aTable ( aText, aNumber ) SELECT @param1 , @param2 FROM Numbers WHERE Numbers.Number<1000 

Numbers表是:

 Number 0 1 2 <...>