Dapper 簡單測試 (二) 插入效能測試

  • 866
  • 0
  • ORM
  • 2018-01-07

續 第一篇簡單測試 後的資料庫插入效能測試

一樣只是簡單的測試,只供參考用途

沒看過的請先看第一篇


想直接看比較結果可以看總整理表

資料類別跟使用的資料庫跟上一篇一樣

每次測試前會先把資料庫重建清空

每輪測試10次,每次 跑 100,000筆資料

並且使用 Transaction 將 100,000筆資料包起來

用Transaction 原因在 mrkt 的程式學習筆記 前輩的 Dapper 練習題 - 新增多筆或大量資料

以下測試僅供參考,不做任何效能保證。

第一次測試 使用 Dapper擴充的 Execute

Stopwatch sw = new Stopwatch();
if (_SqlConnect.State == ConnectionState.Open)
{
    for (int j = 0; j < 10; ++j)
    {
        sw.Reset();
        sw.Start();
        using (var myTransaction = _SqlConnect.BeginTransaction())
        {
            for (int i = 0; i < 100000; ++i)
            {
                string strCom = "INSERT INTO dbo.TestTable (Guid, Name) VALUES (@Guid, @Name)";
                Guid temp = Guid.NewGuid();
                _SqlConnect.Execute(strCom, new { Guid = temp, Name = temp.ToString() }, myTransaction);
            }
            myTransaction.Commit();
            sw.Stop();
            Console.WriteLine($"第{j}次\t{sw.ElapsedMilliseconds.ToString("##,###ms")}");
        }
    }
}
_SqlConnect.Close();

結果如下

第0次   14,341ms
第1次   13,737ms
第2次   13,434ms
第3次   13,370ms
第4次   13,671ms
第5次   13,810ms
第6次   13,666ms
第7次   13,597ms
第8次   13,665ms
第9次   14,037ms

加碼額外測試一下 沒用Transaction的效能

跟上面一樣 只差沒有使用 Transaction

第0次   27,491ms
第1次   27,701ms
第2次   27,363ms
第3次   27,661ms
第4次   27,488ms
第5次   27,193ms
第6次   27,779ms
第7次   27,666ms
第8次   27,535ms
第9次   27,724ms

看了就能比較出效能差異很大了

第二次測試 使用 Dapper.Contrib.Extensions 擴充的 Insert

TestTable test = new TestTable();
test.Guid = Guid.NewGuid();
test.Name = test.Guid.ToString();
_SqlConnect.Insert(test, myTransaction);
第0次   16,593ms
第1次   16,057ms
第2次   16,095ms
第3次   16,183ms
第4次   16,252ms
第5次   15,869ms
第6次   15,811ms
第7次   15,927ms
第8次   15,817ms
第9次   15,840ms

第三次 測試 使用 ADO.Net 直接執行 Insert Data

Guid temp = Guid.NewGuid();
_SqlCmd.Transaction = myTransaction;
_SqlCmd.CommandText = "INSERT INTO dbo.TestTable (Guid, Name) VALUES (@Guid, @Name)";
_SqlCmd.Parameters.Clear();
_SqlCmd.Parameters.AddWithValue("@Guid", temp);
_SqlCmd.Parameters.AddWithValue("@Name", temp.ToString());
_SqlCmd.ExecuteNonQuery();
第0次   13,005ms
第1次   13,305ms
第2次   13,126ms
第3次   13,110ms
第4次   13,209ms
第5次   13,290ms
第6次   13,381ms
第7次   12,986ms
第8次   13,205ms
第9次   13,560ms

 第四次測試 使用 ADO.Net 做 StoredProcedure 插入資料

Guid temp = Guid.NewGuid();
_SqlCmd.Transaction = myTransaction;
_SqlCmd.CommandText = "[uspTestUse]";
_SqlCmd.CommandType = CommandType.StoredProcedure;
_SqlCmd.Parameters.Clear();
_SqlCmd.Parameters.AddWithValue("@param1", temp);
_SqlCmd.Parameters.AddWithValue("@param2", temp.ToString());
_SqlCmd.ExecuteNonQuery();
第0次   13,099ms
第1次   12,881ms
第2次   12,754ms
第3次   12,737ms
第4次   12,659ms
第5次   12,790ms
第6次   12,839ms
第7次   13,027ms
第8次   12,977ms
第9次   13,357ms

第五次測試 使用 Dapper 執行 StoredProcedure

Guid temp = Guid.NewGuid();
_SqlConnect.Execute("uspTestUse"new { param1 = temp, param2 = temp.ToString() },
myTransaction, commandType: CommandType.StoredProcedure);
第0次   13,800ms
第1次   13,605ms
第2次   13,258ms
第3次   13,435ms
第4次   13,570ms
第5次   13,455ms
第6次   13,374ms
第7次   13,173ms
第8次   13,262ms
第9次   13,384ms

心得是 除了 Dapper.Contrib.Extensions 擴充的 Insert 效能比較差之外

其餘效能都差不多,應該是資料類別轉換對應上消耗掉的


最後加碼一組測試 使用 Dapper 做 更新資料

我猜 ADO.Net 效能上應該差不多,所以就不做了

順便測試有做 Index 和 沒有做 Index效能差異,Index 設定是 Id,程式端使用語法相同

這次只做 Id 1~100,000 的更新比較,因為光做一輪更新就等到快死掉了

string strCom = "UPDATE dbo.TestTable SET Guid = @Guid, Name = @Name WHERE Id = @Id";
Guid temp = Guid.NewGuid();
_SqlConnect.Execute(strCom,
    new { Guid = temp, Name = temp.ToString(), Id = j * 100000 + i + 1 },
    myTransaction);
沒用Index的效能
測試結果        2,992,767ms
換算下來大約是 50分鐘左右
使用Index的效能 一般的索引 並非唯一索引
測試結果        14,284ms
效能也差太多了吧
設定成主索引鍵
測試結果        12,876ms

結論是 基本上資料表適當得設定索引鍵,真的會差很多 另外忘記提到說,除了最後一組測試更新之外 查詢跟插入資料都沒有設定索引鍵

Dapper 簡單測試大致上到這了,以後有想到其他可以測試的再補充了


總整理表

第一次測試
使用Dapper的Execute
有使用Transaction
第一次測試
使用Dapper的Execute
沒使用Transaction
第二次測試
使用Dapper的Insert
第三次測試
使用ADO.Net執行
InsertData
第四次測試
使用ADO.Net執行
StoredProcedure
第五次測試
使用Dapper執行
StoredProcedure
第0次14,341ms
第1次13,737ms
第2次13,434ms
第3次13,370ms
第4次13,671ms
第5次13,810ms
第6次13,666ms
第7次13,597ms
第8次13,665ms
第9次14,037ms
第0次27,491ms
第1次27,701ms
第2次27,363ms
第3次27,661ms
第4次27,488ms
第5次27,193ms
第6次27,779ms
第7次27,666ms
第8次27,535ms
第9次27,724ms
第0次16,593ms
第1次16,057ms
第2次16,095ms
第3次16,183ms
第4次16,252ms
第5次15,869ms
第6次15,811ms
第7次15,927ms
第8次15,817ms
第9次15,840ms
第0次13,005ms
第1次13,305ms
第2次13,126ms
第3次13,110ms
第4次13,209ms
第5次13,290ms
第6次13,381ms
第7次12,986ms
第8次13,205ms
第9次13,560ms
第0次13,099ms
第1次12,881ms
第2次12,754ms
第3次12,737ms
第4次12,659ms
第5次12,790ms
第6次12,839ms
第7次13,027ms
第8次12,977ms
第9次13,357ms
第0次13,800ms
第1次13,605ms
第2次13,258ms
第3次13,435ms
第4次13,570ms
第5次13,455ms
第6次13,374ms
第7次13,173ms
第8次13,262ms
第9次13,384ms