Я бы предпочел использовать подвыборы для не сгруппированных значений.
SELECT Forename, Surname,
(SELECT TOP 1 Id FROM myTable mt WHERE mt.Forename = m.Forename AND mt.Surname = m.Surname
ORDER BY m.SomeDate DESC) AS Id
(SELECT TOP 1 SomeDate FROM myTable mt WHERE mt.Forename = m.Forename AND mt.Surname = m.Surname
ORDER BY m.SomeDate DESC) AS SomeDate
FROM myTable m
GROUP BY Forename, Surname
Или вы можете отфильтровать его в предложении WHERE:
SELECT Id, Forename, Surname, SomeDate
FROM myTable m
WHERE m.Id = (SELECT TOP 1 Id FROM myTable mt WHERE mt.Forename = m.Forename AND mt.Surname = m.Surname
ORDER BY m.SomeDate DESC)
Боюсь, что нибудет ужасно эффективным, но тонирование индекса уменьшит это, если необходимо.
Для примера с данными вы бы сделали по сути то же самое.
var recs = from record in dataTable
where record.Id ==
(from rec in dataTable
where rec.Forename == record.Forename && rec.Surname == record.Surname
orderby rec.SomeDate descending
select rec.Id).First()
select record;