SqlDataAdapter 填充 DataSet。Visible = true 顯示結果 (或背景存檔)。using System;
using System.Data;
using System.Data.SqlClient;
using Excel = Microsoft.Office.Interop.Excel;
public class SqlToExcelExporter {
private readonly string _connStr = @"Server=PXGD2;Database=pingxiang;Uid=sa;Pwd=;";
public DataTable GetData() {
using (var conn = new SqlConnection(_connStr))
using (var adapter = new SqlDataAdapter(
"SELECT username AS 用戶名, catalyst_port AS 占用端口, home_address AS 住宅地址, " +
"ip_address AS IP地址, phone AS 電話, addtime AS 開通日期 " +
"FROM userinfo WHERE catalyst_port = 1 OR catalyst_port = 2 ORDER BY ip_address DESC", conn)) {
var ds = new DataSet();
adapter.Fill(ds, "Customer");
return ds.Tables[0];
}
}
public void ExportToExcel() {
var table = GetData();
var excel = new Excel.Application();
try {
excel.Workbooks.Add(true); // 新增活頁簿
int rowIdx = 1, colIdx = 0;
// 寫入標題
foreach (DataColumn col in table.Columns) {
excel.Cells[1, ++colIdx] = col.ColumnName;
}
// 寫入資料
foreach (DataRow row in table.Rows) {
rowIdx++;
colIdx = 0;
foreach (DataColumn col in table.Columns) {
excel.Cells[rowIdx, ++colIdx] = row[col.ColumnName]?.ToString() ?? "";
}
}
excel.Visible = true; // 顯示 Excel 視窗
// 若需背景存檔:excel.ActiveWorkbook.SaveAs(path); excel.Quit();
} finally {
// 注意:COM 物件需手動釋放 (Marshal.ReleaseComObject),此處省略
}
}
}
| 方案 | 優點 | 缺點 |
|---|---|---|
| Excel Interop (本範例) | 完整 Excel 功能、格式控制 | 需安裝 Office、COM 開銷大、不適合伺服器端 |
| EPPlus / ClosedXML | 無需 Office、純 .NET、效能高、支援 .xlsx | 不支援 .xls、無宏功能 |
| NPOI | 支援 .xls/.xlsx、純 .NET | API 較低階 |
| SqlBulkCopy + CSV | 極速、無相依 | 無格式、需後續開啟 |
生產環境強烈建議改用 EPPlus 或 ClosedXML,避免伺服器安裝 Office 且大幅提升效能。
Range.Value = object[,] 陣列一次寫入。Marshal.ReleaseComObject 釋放 Worksheet、Workbook、Application,並呼叫 GC.Collect()。