在 Excel VB 中打开 DataTable
Open DataTable in Excel VB
好的,这是一个有趣的问题。我的任务是修改现有的 VB 项目。当前,用户 select 从一系列下拉列表中编辑到 select 一个 sql 查询,然后 运行 该查询。因此用户 selects 和环境下拉菜单,该下拉菜单的结果填充类别下拉菜单。一旦类别被 selected,他们就会得到可用查询的下拉列表。一旦他们 select 查询并点击 "Run" 按钮,他们就会得到一个包含查询结果的网格视图。有些查询结果很大。我 运行ning 作为测试的查询有 40 列和 20,000 条记录。查询 运行s 不到 5 秒,但渲染 gridview 需要一分多钟。网格视图完成渲染后,用户可以选择将结果导出到 Excel。通过这个,我的意思是代码通过 gridview.RenderControl 打开 Excel 的一个实例,并在 Excel 中显示结果。用户不想保存 excel 文件然后导航到该文件,他们希望它直接从他们正在使用的网络表单打开,这就是代码当前所做的。
然而,用户并不关心gridview。他们根本不在乎是否看到它。他们只想打开 Excel。因此,我不想使用 gridview.RenderControl,而是想打开 Excel 并用内存中的 DataTable(或 DataSet)填充它。有什么想法可以做到这一点吗?
这是他们当前填充网格视图的方式:
将 MyConnection 调暗为 SqlConnection
将 MyCommand 调暗为 SqlCommand
将 MyDataTable 调暗为数据表
将 MyReader 调暗为 SqlDataReader
MyConnection = New SqlConnection()
MyConnection.ConnectionString = ConfigurationManager.ConnectionStrings(Connection).ConnectionString
MyCommand = New SqlCommand()
MyCommand.CommandText = Sqlquery
MyCommand.CommandType = CommandType.Text
MyCommand.Connection = MyConnection
MyCommand.Connection.Open()
MyReader = MyCommand.ExecuteReader(CommandBehavior.CloseConnection)
MyDataTable = New DataTable()
MyDataTable.Load(MyReader)
If (MyDataTable.Rows.Count > 0) Then
QueryresultPanel.Visible = True
gvLineItems.DataSource = MyDataTable
gvLineItems.DataBind()
End If
MyDataTable.Dispose()
MyCommand.Dispose()
MyConnection.Dispose()
这是他们打开和填充 Excel 实例的方式:
Protected Sub btnExportToExcel_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles btnExportToExcel.Click
Response.Clear()
Response.Buffer = True
'
' Set the content type to Excel.
'
Response.AddHeader("content-disposition", "attachment;filename=GridViewExport.xls")
Response.Charset = ""
Response.ContentType = "application/vnd.ms-excel"
'
' Turn off the view state.
'
Me.EnableViewState = False
Dim oStringWriter As New System.IO.StringWriter()
Dim oHtmlTextWriter As New System.Web.UI.HtmlTextWriter(oStringWriter)
'
' Get the HTML for the control.
'
gvLineItems.RenderControl(oHtmlTextWriter)
'
' Write the HTML back to the browser.
'
Response.Write(oStringWriter.ToString())
Response.[End]()
End Sub
显然,DataTable 或 DataSet 没有 RenderControl,无法弄清楚如何让此记录集在 Excel 的实例中呈现,而不先将其保存到文件中。
好的,这是我找到的解决方案(如果有人感兴趣的话)。其实很简单。我只是遍历了数据表并使用了 StringWriter。
Protected Sub WriteToExcelFile(dt As DataTable)
Dim sw As StringWriter
For Each datacol As DataColumn In dt.Columns
sw.Write(datacol.ColumnName + vbTab)
Next
Dim row As DataRow
For Each row In dt.Rows
sw.Write(vbNewLine)
Dim column As DataColumn
For Each column In dt.Columns
If Not row(column.ColumnName) Is Nothing Then
sw.Write(row(column).ToString() + vbTab)
Else
sw.Write(String.Empty + vbTab)
End If
Next column
Next row
Response.Clear()
Response.ContentType = "application/vnd.ms-excel"
Response.AddHeader("Content-Disposition", "attachment;filename=DataTable.xls")
Response.Output.Write(sw.ToString())
Response.Flush()
System.Web.HttpContext.Current.Response.Flush()
System.Web.HttpContext.Current.Response.SuppressContent = True
System.Web.HttpContext.Current.ApplicationInstance.CompleteRequest()
End Sub
好的,这是一个有趣的问题。我的任务是修改现有的 VB 项目。当前,用户 select 从一系列下拉列表中编辑到 select 一个 sql 查询,然后 运行 该查询。因此用户 selects 和环境下拉菜单,该下拉菜单的结果填充类别下拉菜单。一旦类别被 selected,他们就会得到可用查询的下拉列表。一旦他们 select 查询并点击 "Run" 按钮,他们就会得到一个包含查询结果的网格视图。有些查询结果很大。我 运行ning 作为测试的查询有 40 列和 20,000 条记录。查询 运行s 不到 5 秒,但渲染 gridview 需要一分多钟。网格视图完成渲染后,用户可以选择将结果导出到 Excel。通过这个,我的意思是代码通过 gridview.RenderControl 打开 Excel 的一个实例,并在 Excel 中显示结果。用户不想保存 excel 文件然后导航到该文件,他们希望它直接从他们正在使用的网络表单打开,这就是代码当前所做的。
然而,用户并不关心gridview。他们根本不在乎是否看到它。他们只想打开 Excel。因此,我不想使用 gridview.RenderControl,而是想打开 Excel 并用内存中的 DataTable(或 DataSet)填充它。有什么想法可以做到这一点吗?
这是他们当前填充网格视图的方式: 将 MyConnection 调暗为 SqlConnection 将 MyCommand 调暗为 SqlCommand 将 MyDataTable 调暗为数据表 将 MyReader 调暗为 SqlDataReader
MyConnection = New SqlConnection()
MyConnection.ConnectionString = ConfigurationManager.ConnectionStrings(Connection).ConnectionString
MyCommand = New SqlCommand()
MyCommand.CommandText = Sqlquery
MyCommand.CommandType = CommandType.Text
MyCommand.Connection = MyConnection
MyCommand.Connection.Open()
MyReader = MyCommand.ExecuteReader(CommandBehavior.CloseConnection)
MyDataTable = New DataTable()
MyDataTable.Load(MyReader)
If (MyDataTable.Rows.Count > 0) Then
QueryresultPanel.Visible = True
gvLineItems.DataSource = MyDataTable
gvLineItems.DataBind()
End If
MyDataTable.Dispose()
MyCommand.Dispose()
MyConnection.Dispose()
这是他们打开和填充 Excel 实例的方式:
Protected Sub btnExportToExcel_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles btnExportToExcel.Click
Response.Clear()
Response.Buffer = True
'
' Set the content type to Excel.
'
Response.AddHeader("content-disposition", "attachment;filename=GridViewExport.xls")
Response.Charset = ""
Response.ContentType = "application/vnd.ms-excel"
'
' Turn off the view state.
'
Me.EnableViewState = False
Dim oStringWriter As New System.IO.StringWriter()
Dim oHtmlTextWriter As New System.Web.UI.HtmlTextWriter(oStringWriter)
'
' Get the HTML for the control.
'
gvLineItems.RenderControl(oHtmlTextWriter)
'
' Write the HTML back to the browser.
'
Response.Write(oStringWriter.ToString())
Response.[End]()
End Sub
显然,DataTable 或 DataSet 没有 RenderControl,无法弄清楚如何让此记录集在 Excel 的实例中呈现,而不先将其保存到文件中。
好的,这是我找到的解决方案(如果有人感兴趣的话)。其实很简单。我只是遍历了数据表并使用了 StringWriter。
Protected Sub WriteToExcelFile(dt As DataTable)
Dim sw As StringWriter
For Each datacol As DataColumn In dt.Columns
sw.Write(datacol.ColumnName + vbTab)
Next
Dim row As DataRow
For Each row In dt.Rows
sw.Write(vbNewLine)
Dim column As DataColumn
For Each column In dt.Columns
If Not row(column.ColumnName) Is Nothing Then
sw.Write(row(column).ToString() + vbTab)
Else
sw.Write(String.Empty + vbTab)
End If
Next column
Next row
Response.Clear()
Response.ContentType = "application/vnd.ms-excel"
Response.AddHeader("Content-Disposition", "attachment;filename=DataTable.xls")
Response.Output.Write(sw.ToString())
Response.Flush()
System.Web.HttpContext.Current.Response.Flush()
System.Web.HttpContext.Current.Response.SuppressContent = True
System.Web.HttpContext.Current.ApplicationInstance.CompleteRequest()
End Sub