12,925
回編集
688行目: | 688行目: | ||
{ | { | ||
Console.WriteLine($"エラーが発生: {ex.Message}"); | Console.WriteLine($"エラーが発生: {ex.Message}"); | ||
} | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br><br> | |||
== 大量データの高速処理 == | |||
以下の例では、100万行のデータを生成して、Excelファイルに高速で書き込んでいる。<br> | |||
<br> | |||
* Enumerable.RangeとLINQを使用して大量のデータを効率的に生成する。 | |||
* InsertDataメソッドを使用して、データを一括で挿入する。<br>これは、個別のセルに値を設定するよりも高速である。 | |||
<br> | |||
大量のデータを扱う場合は、MemoryStreamのサイズが大きくなる可能性がある。<br> | |||
そのような場合は、データを分割して処理、あるいは、ストリーミング方式でファイルに書き込む方法を検討する必要がある。<br> | |||
<br> | |||
<u>※注意</u><br> | |||
<u>Closed XMLには直接的な非同期メソッドが存在しないため、これを回避するための1つの方法である。</u><br> | |||
<u>Closed XMLの将来のバージョンで非同期メソッドが提供された場合は、それを使用するように更新することを推奨する。</u><br> | |||
<br> | |||
<syntaxhighlight lang="c#"> | |||
using System; | |||
using System.Diagnostics; | |||
using System.IO; | |||
using System.Linq; | |||
using System.Threading.Tasks; | |||
using ClosedXML.Excel; | |||
class Program | |||
{ | |||
static async Task Main(string[] args) | |||
{ | |||
Console.WriteLine("大量データの完全非同期高速処理を開始..."); | |||
var stopwatch = Stopwatch.StartNew(); | |||
try | |||
{ | |||
await ProcessLargeDataAsync(); | |||
stopwatch.Stop(); | |||
Console.WriteLine($"大量データの処理が完了 処理時間: {stopwatch.ElapsedMilliseconds}ms"); | |||
} | |||
catch (Exception ex) | |||
{ | |||
Console.WriteLine($"エラーが発生しました: {ex.Message}"); | |||
} | |||
} | |||
static async Task ProcessLargeDataAsync() | |||
{ | |||
var workbook = await Task.Run(() => | |||
{ | |||
var wb = new XLWorkbook(); | |||
var worksheet = wb.Worksheets.Add("大量データ"); | |||
// 100万行のデータを生成 | |||
const int rowCount = 1_000_000; | |||
var data = Enumerable.Range(1, rowCount) | |||
.Select(i => new { ID = i, Value = i * 2 }) | |||
.ToList(); | |||
// データをワークシートに書き込む | |||
worksheet.Cell(1, 1).Value = "ID"; | |||
worksheet.Cell(1, 2).Value = "Value"; | |||
worksheet.Cell(2, 1).InsertData(data); | |||
// 合計を計算 | |||
worksheet.Cell(rowCount + 2, 1).Value = "合計"; | |||
worksheet.Cell(rowCount + 2, 2).FormulaA1 = $"=SUM(B2:B{rowCount + 1})"; | |||
return wb; | |||
}); | |||
// ファイルを非同期で保存 | |||
await SaveWorkbookAsync(workbook, "大量データ処理.xlsx"); | |||
} | |||
static async Task SaveWorkbookAsync(XLWorkbook workbook, string filePath) | |||
{ | |||
using (var memoryStream = new MemoryStream()) | |||
{ | |||
workbook.SaveAs(memoryStream); | |||
memoryStream.Position = 0; | |||
using (var fileStream = new FileStream(filePath, FileMode.Create, FileAccess.Write, FileShare.None, bufferSize: 4096, useAsync: true)) | |||
{ | |||
await memoryStream.CopyToAsync(fileStream); | |||
} | |||
} | } | ||
} | } |