2016-10-07 2 views
2

Ich habe ein Wörterbuch, das Informationen aus einem geparsten Testlauf enthält. Der Schlüssel ist der Name der Methode und der Wert ist eine Liste von TestRunProperties. Mein Wörterbuch enthält alle Methoden eines Testlaufs und ich möchte die Methoden entfernen, die während eines Testlaufs fehlgeschlagen sind. Ist das mit Linq möglich?Entfernen bestimmter Werte aus einem Dictionary C# mit Linq

TestRunProperties Klasse:

public class TestRunProperties 
{ 
    public string computerName { get; set; } 
    public TimeSpan duration { get; set; } 
    public string startTime { get; set; } 
    public string endTime { get; set; } 
    public string testName { get; set; } 
    public string outcome { get; set; } 
} 

Wörterbuch:

//Key is the name of the method, value is the properties associated with each run 
private static Dictionary<string, List<TestRunProperties>> runResults = new Dictionary<string, List<TestRunProperties>>(); 

Ich habe dies versucht, aber ich glaube, ich bin immer mit dem Where Teil verwirrt:

runResults.Remove(runResults.Where(methodName => methodName.Value.Where(method => method.outcome.ToLower().Equals("failed")))); 

I‘ Ich bin ziemlich neu bei Linq und Lambda und versuche immer noch zu verstehen, wie man auf solche Daten zugreifen kann.

+0

Vielen Dank für Ihre Hilfe, alle wirklich großen Antworten! – Novastorm

Antwort

3

Verwenden Sie einfach eine Schleife, um die Elemente zu entfernen, die Sie nicht möchten. Sie können eine Erweiterungsmethode schreiben, um es einfacher zu nennen:

public static class DictionaryExt 
{ 
    public static void RemoveAll<K, V>(this IDictionary<K, V> dict, Func<K, V, bool> predicate) 
    { 
     foreach (var key in dict.Keys.ToArray().Where(key => predicate(key, dict[key]))) 
      dict.Remove(key); 
    } 
} 

Dies wird in der Regel effizienter sein als ein völlig neues Wörterbuch zu schaffen, vor allem, wenn die Anzahl der Elemente im Vergleich relativ niedrig ist, von der die Größe entfernt werden Wörterbuch.

Ihre Berufung Code würde wie folgt aussehen:

runResults.RemoveAll((key, methodName) => methodName.Value.Where(method => method.outcome.ToLower().Equals("failed"))); 

(ich den Namen RemoveAll() wählte List.RemoveAll() übereinstimmen.)

0

Um sind Sie wahrscheinlich besser dran, ein neues Wörterbuch aus dem bestehenden Auswahl ehrlich:

runResults.Select().ToDictionary(x => x.Key, x => x.Value.Where(x => x.Value.outcome != "failed")); 

* editierte widerzuspiegeln Liste im Wörterbuch.

Eigentlich kann man ohne erfolgreiche Ergebnisse von denen, loszuwerden, indem dies zu tun:

runResults.Select(x => new { x.Key, x.Value.Where(x => x.Value.outcome != "failed")}).Where(x => x.Value.Any()).ToDictionary(x => x.Key, x => x.Value); 
+0

Ich denke, dass ein Teil fehlt mit dem oben genannten; Wert ist eine Liste und nicht eine einzelne TestRunProperty, so kann ich nicht auf die .outcome von ihr zugreifen – Novastorm

+0

Ah, so müssen Sie nur eine Ebene mehr abfragen – gmn

1

Sie könnten ein neues Wörterbuch erstellen, indem Sie die ungültig diejenigen herausgefiltert werden:

var filtered = runResults.ToDictionary(p => p.Key, p => p.Value.Where(m => m.outcome.ToLower() != "failed").ToList()); 

Ok , grrrrrr war schneller :-)

+0

Vielen Dank, das hat funktioniert! grrrrrr Antwort war in der Nähe, aber verpasste einen oder zwei Punkte :) – Novastorm

Verwandte Themen