2

I have data like the following inside my DataTable:

   id   vrn   seenDate
   ---  ----  --------

    1   ABC   2017-01-01 20:00:05
    2   ABC   2017-01-01 18:00:09
    3   CCC   2016-05-05 00:00:00

I am trying to modify the data to only show vrn values with the most recent date. This is what I have done so far:

myDataTable.AsEnumerable().GroupBy(x => x.Field<string>("vrn")).Select(x => new { vrn = x.Key, seenDate = x.Max(y => y.Field<DateTime>("seenDate")) });

I need to modify the above to also select the id field (i.e. I do not want to group on this field, but I want to have it included in the resulting data set).

I cannot put in x.Field<int>("id") in the Select() part, as the Field clause does not exist.

Shadow
  • 33,525
  • 10
  • 51
  • 64
MathLover
  • 81
  • 8

3 Answers3

5

You need an equivalent of MaxBy method from MoreLINQ.

In standard LINQ it can be emulated with OrderByDescending + First calls:

var result = myDataTable.AsEnumerable()
    .GroupBy(x => x.Field<string>("vrn"))
    .Select(g => g.OrderByDescending(x => x.Field<DateTime>("seenDate")).First())
    .Select(x => new
    {
        vrn = x.Field<string>("vrn"),
        id = x.Field<int>("id"),
        seenDate = x.Field<DateTime>("seenDate"),
    });
Ivan Stoev
  • 195,425
  • 15
  • 312
  • 343
0

You can use select new like this to select anything you want from your data

var query = from pro in db.Projects
                select new { pro.ProjectName, pro.ProjectId };
FelixSFD
  • 6,052
  • 10
  • 43
  • 117
M.h Basiri
  • 56
  • 9
0

If you may have few ids in the same vrn with same max date then the following would work:

IEnumerable<DataRow> rows = myDataTable.AsEnumerable()
    .GroupBy(x => x.Field<string>("vrn"))
    .Select(x => new 
    {
        Grouping = x, 
        MaxSeenDate = x.Max(y => y.Field<DateTime>("seenDate"))
    })
    .SelectMany(arg => 
        arg.Grouping.Where(y => y.Field<DateTime>("seenDate") == arg.MaxSeenDate));

It will retrun an IEnumerable of the original DataRow so you have all your fields there.

Or you can add another select to have only the fields you need.

Ofir Winegarten
  • 9,215
  • 2
  • 21
  • 27