开发者

Getting minimum - Min() - for DateTime column in a DataTable using LINQ to DataSets?

I need to get the minimum DateTime value of a column in a DataTable. The DataTable is generated dynamically from a CSV file, therefore I don't know the name of that column until runtime. Here is code I've got that doesn't work...

private DateTime GetStartDateFromCSV(string inputFile, string date_attr)
{
    EnumerableRowCollection<DataRow> table = CsvStreamReader.GetDataTableFromCSV(inputFile, "input", true).AsEnumerable();
    DateTime dt = table.Select(record => record.Field<DateTime>(date_attr)).Min();
    return dt;
}

The variable table is broken out just for clarity. I basically need to find the minimum value as a DateTime for one of the columns (to be chosen at runtime and represented by date_attr).

I have tried several solutions from SO (most deal with known columns and/or non-DateTime fields). W开发者_运维技巧hat I've got throws an error at runtime telling me that it can't do the DateTime conversion (that seems to be a problem with Linq?)

I've confirmed that the data for the column name that is in the string date_attr is a date value.

UPDATE: Stacktrace as requested:

System.InvalidCastException was unhandled by user code
  Message="Specified cast is not valid."
  Source="System.Data.DataSetExtensions"
  StackTrace:
       at System.Data.DataRowExtensions.UnboxT`1.ValueField(Object value)
       at System.Data.DataRowExtensions.Field[T](DataRow row, String columnName)
       at Presenter.Views.NetworkVisualizationDetailPresenter.<>c__DisplayClass1.<GetStartDateFromCSV>b__0(DataRow t) in Presenter\Views\NetworkVisualizationDetailPresenter.cs:line 194
       at System.Linq.Enumerable.WhereSelectEnumerableIterator`2.MoveNext()
       at System.Linq.Enumerable.Min[TSource](IEnumerable`1 source)
       at System.Linq.Enumerable.Min[TSource,TResult](IEnumerable`1 source, Func`2 selector)
       atPresenter.Views.NetworkVisualizationDetailPresenter.GetStartDateFromCSV(String inputFile, String date_attr) in Presenter\Views\NetworkVisualizationDetailPresenter.cs:line 194
       at Presenter.Views.NetworkVisualizationDetailPresenter.GetDynamicNetworkVisualizationData(String inputFile, Int32 dataMode, Int32 timeInterval, String date_attr, String entity_attr, String event_attr) in Views\NetworkVisualizationDetailPresenter.cs:line 123
       at Presenter.Views.NetworkVisualizationDetail.Page_Load(Object sender, EventArgs e) in NetworkVisualizationDetail.aspx.cs:line 114
       at System.Web.Util.CalliHelper.EventArgFunctionCaller(IntPtr fp, Object o, Object t, EventArgs e)
       at System.Web.Util.CalliEventHandlerDelegateProxy.Callback(Object sender, EventArgs e)
       at System.Web.UI.Control.OnLoad(EventArgs e)
       at System.Web.UI.Control.LoadRecursive()
       at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
  InnerException: 


Actually it seems like your problem is not in Linq, but in the data in your data table. If your error states that is can't do the DateTime conversion, your error most likely is generated here:

record.Field<DateTime>(date_attr)

which isn't in Linq.

Check that all of your rows have the correct value in this column. Also, if you could dump your stack trace from the exception it would help..

UPD: Looking at the stack trace update, I can see the top 2 entries in it:

at System.Data.DataRowExtensions.UnboxT`1.ValueField(Object value)
at System.Data.DataRowExtensions.Field[T](DataRow row, String columnName)

This most definitely confirms that the problem is not inside linq, but in the actual data that you're trying to convert. Second call is the exception message, definitely a data conversion problem:

Message="Specified cast is not valid."

I have just double checked, this code would work on a datatable, if the column type were DateTime.

table.Select(record => record.Field<DateTime>(date_attr)).Min();

But if the column type is string - it throws the exception you're getting, with the same stack trace! :)

Change it to this, and you shouldn't get any errors (that is considering your data is valid):

table.Select(record => Convert.ToDateTime(record[date_attr])).Min();
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜