C#のDataTableのループ読み取り(参照)が遅い問題の解決策

作成日:
DataTableについて

DataTableはインデックスを使ったアクセスが遅いようで、ネットを検索してみてもそのような記事がちらほらありました。そこでいろいろ調べた結果、foreach文で回すことでそれなりに改善できたのでその備忘録です。

改善前)

DataTable dataTable;
dataTable = (データをセット)
var cellValue = string.Empty;
// DataTable 読み込み処理
foreach (DataRow dataRow in dataTable.Rows)
{
    // 列をforループで読み取り
    for (var i = 0; i < dataRow.ItemArray.Length; i++)
    {
        cellValue = dataRow[i].ToString(); ←ここが遅い (CellValueをobject型にして cellValue = dataRow[i] としても同様)
        // この次に cellValue を Excel出力
    }
}
これを↓のようにforeach文でループするように変更。
DataTable dataTable;
dataTable = (データをセット)
var cellValue = string.Empty;
// DataTable 読み込み処理
foreach (DataRow dataRow in dataTable.Rows)
{
    // 列をforループで読み取り
    foreach (var col in dataRow.ItemArray)
    {
        cellValue = col.ToString();
        // この次に cellValue を Excel出力
    }
}

OpenXML SDK 2.0でExcelファイルを出力する処理なのですが、DataTableのサイズが約46,000行×580列(約27,000,000セル分)のとき、修正前は25分くらい掛かっていたのが7分前後で処理できるようになりました。3.5倍くらい高速化しました。もっと高速化する方法があるかもしれませんが、とりあえずこれで良しとします。

参考サイト

(.Net)DataTableへのアクセスで列名で指定すると遅くなる
https://jehupc.exblog.jp/17968196/

関連記事