C# 如何从ObjectDataSource的LINQ查询中删除空列
如问题所示,我想从LINQ查询中删除所有列,其中该列中的所有行都为空 在我使用LINQ运行带有所需日期和站点筛选器的初始查询时,这会将IEnumerable对象返回到GridView中的ObjectDataSource。这一切都很好 但是我很难实现删除空/空列的代码(LINQ对我来说是非常新的) 以下是我将IEnumerable返回到ObjectDataSource的工作代码:C# 如何从ObjectDataSource的LINQ查询中删除空列,c#,asp.net,sql-server,linq,datatable,C#,Asp.net,Sql Server,Linq,Datatable,如问题所示,我想从LINQ查询中删除所有列,其中该列中的所有行都为空 在我使用LINQ运行带有所需日期和站点筛选器的初始查询时,这会将IEnumerable对象返回到GridView中的ObjectDataSource。这一切都很好 但是我很难实现删除空/空列的代码(LINQ对我来说是非常新的) 以下是我将IEnumerable返回到ObjectDataSource的工作代码: public IEnumerable<WebApplication1.HL_Log> Select(str
public IEnumerable<WebApplication1.HL_Log> Select(string startDate, string endDate)
{
DateTime start = DateTime.Now.AddDays(-1);
DateTime end = DateTime.Now;
if (startDate != "01/01/1900")
{
DateTime.TryParse(startDate, out start);
}
if (endDate != "01/01/1900")
{
DateTime.TryParse(endDate, out end);
}
DataClasses1DataContext db = new DataClasses1DataContext();
var query = from h in db.HL_Logs
where h.ID_Location == 45
&& h.Time_Stamp >= start.Date
&& h.Time_Stamp <= end.Date.AddDays(1)
orderby h.Time_Stamp
select h;
return query;
}
public IEnumerable选择(字符串开始日期、字符串结束日期)
{
DateTime start=DateTime.Now.AddDays(-1);
DateTime end=DateTime.Now;
如果(起始日期!=“01/01/1900”)
{
DateTime.TryParse(开始日期,结束日期);
}
如果(结束日期!=“01/01/1900”)
{
DateTime.TryParse(endDate,out-end);
}
DataClasses1DataContext db=新DataClasses1DataContext();
var query=从db.HL_日志中的h开始
其中h.ID_位置==45
&&时间戳>=开始日期
&&时间戳dr.IsNull(列)))
dt.列。移除(列);
}
但我需要将其转换回IEnumerable,然后才能将其返回到ObjectDataSource。所以我的问题是,如何将数据表转换回IEnumerable,或者我是否使用了一种非常低效的方法,如果是的话,实现结果的最佳方法是什么
到目前为止,我的总体代码如下:
public IEnumerable<WebApplication1.HL_Log> Select(string startDate, string endDate)
{
DateTime start = DateTime.Now.AddDays(-1);
DateTime end = DateTime.Now;
if (startDate != "01/01/1900")
{
DateTime.TryParse(startDate, out start);
}
if (endDate != "01/01/1900")
{
DateTime.TryParse(endDate, out end);
}
DataClasses1DataContext db = new DataClasses1DataContext();
var query = from h in db.HL_Logs
where h.ID_Location == 45
&& h.Time_Stamp >= start.Date
&& h.Time_Stamp <= end.Date.AddDays(1)
orderby h.Time_Stamp
select h;
//Convert to a Datatable
DataTable dt = new DataTable();
dt = LINQToDataTable(query);
//Now remove the completely NULL columns
foreach(var column in dt.Columns.Cast<DataColumn>().ToArray())
{
if (dt.AsEnumerable().All(dr => dr.IsNull(column)))
dt.Columns.Remove(column);
}
//return ""HELP"";
}
public IEnumerable选择(字符串开始日期、字符串结束日期)
{
DateTime start=DateTime.Now.AddDays(-1);
DateTime end=DateTime.Now;
如果(起始日期!=“01/01/1900”)
{
DateTime.TryParse(开始日期,结束日期);
}
如果(结束日期!=“01/01/1900”)
{
DateTime.TryParse(endDate,out-end);
}
DataClasses1DataContext db=新DataClasses1DataContext();
var query=从db.HL_日志中的h开始
其中h.ID_位置==45
&&时间戳>=开始日期
&&时间戳dr.IsNull(列)))
dt.列。移除(列);
}
//返回“帮助”;
}
谢谢你的帮助 TL;DR 如果
Select
方法的使用者是GridView-DataBind()
,并且您需要一个完全动态的解决方案(例如GridView
可以绑定到hlu-Log
以外的其他类型),那么您最好还是返回过滤后的数据表
解决方案,因为很难针对未知类型的任意集合实现动态行隐藏
老实说,我看不到更好的通用方法来实现您已经在做的事情-需要像DataTable
、Xml
或ExpandoObject
这样的AIK元数据吗
更详细的信息
由于您的方法返回强类型实体的枚举(IEnumerable
),因此您不能有选择地从该实体中“删除”属性或字段-所有hlu Log
的实例都将具有所有属性。我假设您当前在GridView中将AutoGenerateColumns
设置为true
,因此需要修剪源代码中无用的列。根据数据库列的所有值是否为空(例如,尝试返回IEnumerable和ExpandoObject
)来投影不同的类型也将很困难/繁琐
此方法的另一种替代方法是将列作为表示层问题隐藏在GridView
中。但是请注意,这意味着您需要将AutoGenerateColumns
设置更改为false
(),并明确检查Hl\u Log
var hlLogs = myObject.Select(someStartDate, someEndDate).ToList();
if (hlLogs.All(hl => hl.Property1 == null))
{
myGridView.Columns["Property1"].Visible = false;
}
// Same for Property2, etc.
这当然会很快变得单调乏味。查看现有代码可能会重复,我相信OP希望筛选列,而不是行,以便在GridView
中隐藏它们。感谢您的回复,我如何按照您的建议将数据库返回到objectdatasource?正如您所提到的,在表示级别修改gridview将非常繁琐,因此我想尝试避免这种情况……我想说的是,如果该方法返回IEnumerable
,然后绑定到gridview
,那么您将显式需要选中。All()
查看每列是否应隐藏该列。您可能可以使用反射(获取实体的所有属性),然后迭代行,但这一切都相当混乱。您的原始设计返回了数据表
(或其他元数据)可能与它得到的一样简单?将此标记为答案,因为您的建议帮助我产生了我想要的结果。。您是否可以通过编辑问题来粘贴或描述您的解决方案?这将帮助未来的用户:)
var hlLogs = myObject.Select(someStartDate, someEndDate).ToList();
if (hlLogs.All(hl => hl.Property1 == null))
{
myGridView.Columns["Property1"].Visible = false;
}
// Same for Property2, etc.