You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ASP.NET C#中为单个GridView配置两个数据源的问题

解决单个GridView绑定两个数据源的问题

问题根源

你的代码无法正常显示数据的原因有两个:

  1. GridView未绑定任何数据源:没有给GridView指定DataSource并执行DataBind(),导致不会生成数据行,RowDataBound事件也不会触发(仅表头会渲染)。
  2. DataItem无法跨数据源获取字段:即使绑定了某一个数据源,该行的DataItem仅包含当前数据源的字段,无法直接获取另一个数据源的Name或Country值。

以下提供两种无需SQL端操作(存储过程/联表)的解决方案,完全在Visual Studio的ASP.NET代码中实现:


方案一:合并两个数据源为统一DataTable后绑定

这种方式将两个数据源的数据合并到一个新的DataTable中,再绑定到GridView,逻辑清晰且易于维护。

前端代码(保持原结构即可)

<asp:GridView ID="GridView1" runat="server">
    <Columns>
        <asp:BoundField DataField="BasSaat" HeaderText="BasSaat" />
        <asp:BoundField DataField="Ad" HeaderText="Ad" />
    </Columns>
</asp:GridView>

<asp:SqlDataSource ID="SqlDataSource2" runat="server" ConnectionString="<%$ ConnectionStrings:RemoteConnect %>" SelectCommand="SELECT [Name] FROM [Table1]"></asp:SqlDataSource>
<asp:SqlDataSource ID="SqlDataSource1" runat="server" ConnectionString="<%$ ConnectionStrings:RemoteConnect %>" SelectCommand="SELECT [Country] FROM [Table2]"></asp:SqlDataSource>

后台代码

protected void Page_Load(object sender, EventArgs e)
{
    if (!IsPostBack)
    {
        // 从两个SqlDataSource中提取数据
        DataTable dtCountry = GetDataSourceData(SqlDataSource1);
        DataTable dtName = GetDataSourceData(SqlDataSource2);

        // 创建合并后的DataTable,对应GridView的列
        DataTable mergedTable = new DataTable();
        mergedTable.Columns.Add("BasSaat", typeof(string));
        mergedTable.Columns.Add("Ad", typeof(string));

        // 处理两个数据源行数不一致的情况,取最大行数填充
        int maxRowCount = Math.Max(dtCountry.Rows.Count, dtName.Rows.Count);
        for (int i = 0; i < maxRowCount; i++)
        {
            DataRow newRow = mergedTable.NewRow();
            // 填充第一个列(来自SqlDataSource1的Country)
            newRow["BasSaat"] = i < dtCountry.Rows.Count ? dtCountry.Rows[i]["Country"].ToString() : string.Empty;
            // 填充第二个列(来自SqlDataSource2的Name)
            newRow["Ad"] = i < dtName.Rows.Count ? dtName.Rows[i]["Name"].ToString() : string.Empty;
            
            mergedTable.Rows.Add(newRow);
        }

        // 绑定合并后的表到GridView
        GridView1.DataSource = mergedTable;
        GridView1.DataBind();
    }
}

// 辅助方法:从SqlDataSource获取DataTable
private DataTable GetDataSourceData(SqlDataSource dataSource)
{
    DataView dataView = (DataView)dataSource.Select(DataSourceSelectArguments.Empty);
    return dataView.ToTable();
}

方案二:绑定单个数据源,在RowDataBound中填充第二个数据源数据

这种方式先绑定其中一个数据源,再在行绑定事件中从另一个数据源提取对应行的数据填充到列中。

前端代码(保持原结构,保留RowDataBound事件)

<asp:GridView ID="GridView1" runat="server" OnRowDataBound="GridView1_RowDataBound">
    <Columns>
        <asp:BoundField DataField="BasSaat" HeaderText="BasSaat" />
        <asp:BoundField DataField="Ad" HeaderText="Ad" />
    </Columns>
</asp:GridView>

<asp:SqlDataSource ID="SqlDataSource2" runat="server" ConnectionString="<%$ ConnectionStrings:RemoteConnect %>" SelectCommand="SELECT [Name] FROM [Table1]"></asp:SqlDataSource>
<asp:SqlDataSource ID="SqlDataSource1" runat="server" ConnectionString="<%$ ConnectionStrings:RemoteConnect %>" SelectCommand="SELECT [Country] FROM [Table2]"></asp:SqlDataSource>

后台代码

// 存储第二个数据源的数据,供RowDataBound事件使用
private List<string> _nameList;

protected void Page_Load(object sender, EventArgs e)
{
    if (!IsPostBack)
    {
        // 提取SqlDataSource2的Name数据并存储
        DataTable dtName = GetDataSourceData(SqlDataSource2);
        _nameList = dtName.AsEnumerable().Select(row => row["Name"].ToString()).ToList();

        // 绑定SqlDataSource1到GridView
        GridView1.DataSource = SqlDataSource1;
        GridView1.DataBind();
    }
}

private DataTable GetDataSourceData(SqlDataSource dataSource)
{
    DataView dataView = (DataView)dataSource.Select(DataSourceSelectArguments.Empty);
    return dataView.ToTable();
}

protected void GridView1_RowDataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        // 填充第一个列:当前绑定数据源的Country字段
        e.Row.Cells[0].Text = ((DataRowView)e.Row.DataItem)["Country"].ToString();
        
        // 填充第二个列:从预存的列表中取对应索引的数据,超出范围则为空
        int rowIndex = e.Row.RowIndex;
        e.Row.Cells[1].Text = rowIndex < _nameList.Count ? _nameList[rowIndex] : string.Empty;
    }
}

内容的提问来源于stack exchange,提问作者Ali Mohammad alizadeh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 19:18:31