![](/img/trans.png)
[英]How to convert multiple rows into one row with multiple columns using Pivot in SQL Server when data having NULL values
[英]Using StringBuilder and a DataTable, How do I return multiple rows in three columns without breaking when there is only one row?
我有一个函数,该函数根据调用的ID从SQL存储的Proc返回电子邮件地址列表。 它使用StringBuilder并返回一列。 对于大多数ID,电子邮件地址为4个或更少,这种格式很好。 但是,我们现在获得了更多具有10多个电子邮件地址的ID,这使页面过长。
该函数是:
DataTable dt = DAL.ExecStoredProc(DAL.DatabaseName.DB, "storedProc", param);
StringBuilder sb = new StringBuilder();
sb.Append("<br/><br/>");
sb.Append("<table border='0' cellpadding='3'>");
for (int i = 0; i < dt.Rows.Count; i++)
{
sb.Append("<tr><td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
sb.Append("</td></tr>");
}
sb.Append("</table>");
return sb.ToString();
我尝试使用以下内容,但是在返回的地址太少时会中断:
DataTable dt = DAL.ExecStoredProc(DAL.DatabaseName.DB, "storedProc", param);
StringBuilder sb = new StringBuilder();
sb.Append("<br/><br/>");
sb.Append("<table border='0' cellpadding='3'>");
for (int i = 0; i < dt.Rows.Count; i++)
{
sb.Append("<tr><td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
i++;
sb.Append("</td>");
sb.Append("<td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
i++;
sb.Append("</td>");
sb.Append("<td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
i++;
sb.Append("</td></tr>");
}
sb.Append("</table>");
return sb.ToString();
使用Linq的Take
函数,您可以从第一个示例中替换以下代码块:
for (int i = 0; i < dt.Rows.Count; i++)
{
sb.Append("<tr><td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
sb.Append("</td></tr>");
}
有了这个:
foreach (var row in dt.Rows.OfType<DataRow>().Take(3))
{
sb.Append("<tr><td>");
sb.Append(row["EMail"].ToString());
sb.Append("</td></tr>");
}
由于Take从序列的开头最多返回指定数量的元素,因此该代码块将在0到3次之间任意运行。 您最多将显示3个地址(即使存在更多地址),如果少于3个,则不会获得IndexOutOfRangeException
。
更新:与ASP.NET 2.0兼容
由于您不能使用Linq,因此结果应相同:
for (int i = 0; i < (dt.Rows.Count > 3 ? 3 : dt.Rows.Count); i++)
{
sb.Append("<tr><td>");
sb.Append(dt.Rows[i]["EMail"].ToString());
sb.Append("</td></tr>");
}
表达式dt.Rows.Count > 3 ? 3 : dt.Rows.Count
dt.Rows.Count > 3 ? 3 : dt.Rows.Count
使用?
运算符使for
循环遍历所有电子邮件地址,除非有3个以上,否则将仅循环3次。
您可以考虑使用asp.net转发器控件,而不是使用字符串生成器构建html表。 您可以将DataTable直接绑定到转发器,然后从html设计图面控制html。 对于您想做的事情,它将被证明更加灵活。 这是假设您正在使用asp.net。
另请参阅我关于创建自定义asp.net控件的文章,因为这将为您提供最大的灵活性并封装您的自定义html逻辑。
请享用!
我认为Doug走在正确的轨道上,但是如果您坚持使用StringBuilder和for循环来做到这一点,请尝试以下操作:
DataTable dt = DAL.ExecStoredProc(DAL.DatabaseName.DB, "storedProc", param);
StringBuilder sb = new StringBuilder();
sb.Append("<br/><br/>");
sb.Append("<table border='0' cellpadding='3'>");
string rowFormat = "<tr><td>{0}</td><td>{1}</td><td>{2}</td></tr>";
for (int i = 0; i < dt.Rows.Count; i+=3)
{
string[] rowEmails = { String.Empty, String.Empty, String.Empty };
for (int j = 0; j < 3; j++)
{
if (i+j < dt.Rows.Count) rowEmails[j] = dt.Rows[i+j]["Email"].ToString();
}
sb.AppendFormat(rowFormat, rowEmails[0], rowEmails[1], rowEmails[2]);
}
sb.Append("</table>");
return sb.ToString();
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.