Visual Studio 2019; ASP.Net Core 2.1
J'ai un système de base de données qui a un tableau des événements qui se produisent sur différentes machines.
8/2/2004 8:05:27 PM / 5/2/2019 12:00:00 AM
Je veux récupérer l'événement le plus ancien et le plus récent dates pour une machine particulière. Dans SSMS, je peux obtenir les informations que je veux avec:
public class VisibleRange { public DateTime start { get; set; } public DateTime end { get; set; } } ... var ctx = userTrackingContext.EventLog; usertrackingRange = ( from eventLog in userTrackingContext.EventLog where eventLog.Machine.ToUpper().Split( '.', StringSplitOptions.RemoveEmptyEntries )[0].Trim().Equals(myMachine) select eventLog.Date ).Select(range => new VisibleRange { start = ctx.Min(a => a.Date), end = ctx.Max(a => a.Date) }).First();
Dans un exemple d'exécution, j'obtiens des valeurs min / max de:
2015-08-17 10:31:47.000 / 2019-05-02 12:54:20.000
Remarque: machineName
peut être une chaîne "simple" comme "mypc" ou un FQDN ("mypc.company.com"). J'ai divisé le premier segment "pointillé" du FQDN possible et je le compare à la variable myMachine
qui a déjà eu des parties pointillées supprimées.
En C #, je suis conscient qu'il y a sont des méthodes agrégées
mais j'ai du mal à suivre les documents et les exemples que j'ai trouvés et à les traduire dans la pratique réelle. J'ai jusqu'à présent:
SELECT MIN([eventDate]), MAX([eventDate]) FROM eventLog WHERE UPPER(machineName) LIKE 'MY-MACHINENAME%';
Cela fonctionne mais ne me donne pas de résultats utiles pour la valeur Min. Ce délai est d'environ 11 ans.
// pseudo code eventLog ( id int primary key not null, eventType varchar(16) not null, machineName varchar(64) not null, loggedInUser varchar(16) not null, eventDate datetime not null, )
Comment puis-je convertir la requête SSMS en requête LINQ?
3 Réponses :
Vous pouvez essayer de suivre la requête LINQ
usertrackingRange = ( from eventLog in userTrackingContext.EventLog where eventLog.Machine.ToUpper().Split( '.', StringSplitOptions.RemoveEmptyEntries )[0].Trim().Equals(myMachine) select eventLog.Date ).Select(range => new VisibleRange { start = ctx.OrderByAscending(a => a.Date).First(), end = ctx.OrderByDescending(a => a.Date).First() }).First();
Dans les lignes ctx.OrderBy ...
, on me dit que je ne peux pas convertir du type ctx
en DateHeure
. Je ne vois pas de moyen de contraindre cela.
J'ai fait un test de fumée rapide et vos sélections fonctionnent pour moi. Pourquoi n'appelez-vous pas range.Min et range.Max pour obtenir les résultats de votre ensemble de données filtré?
var now = DateTime.Now; var nums = new List<Num> { new Num { Min = now, Max = now.AddDays(1) }, new Num { Min = now.AddDays(10), Max = now.AddDays(50) }, new Num { Min = now.AddDays(51), Max = now.AddDays(100) }, }; var minMaxNum = nums.Select(num => new Num { Min = nums.Min(_ => _.Min), Max = nums.Max(_ => _.Max), }).First();
Vous pouvez essayer comme: -
var range = new VisibleRange() { }; var matched = userTrackingContext.EventLog.Where(a => a.MachineName.StartsWith(myMachine)); if(matched != null) { range.start = matched.Min(a => a.EventDate); range.end = matched.Max(a => a.EventDate); }