I have two classes:
public GeneralClassName
{
public GeneralClassName ()
{
SpecificList = new List<OtherClass>();
}
public string StringValue;
public string OtherStringValue;
public List<OtherClass> SpecificList;
}
and
public OtherClass
{
public string Name;
public string Number;
}
After a JSON deserialization I obtain a nice List<GeneralClassName>, the result I want is a Dictionary<string, int> whose value is the sum of the variabiles “Number” inside List<OtherClass> inside List<GeneralClassName>, while the key is the variabile Name.
In other words I’d like to sum Number grouping by Name.
Now, the only thing that came across my mind is a nested foreach, something like that:
Dictionary<string, int> resultDictionary = new Dictionary<string, int>();
foreach(List<OtherClass> listOtherClass in bigListGeneralClass.Select(x => x.SpecificList))
{
foreach(OtherClass otherClass in listOtherClass)
{
int value = 0;
if(resultDictionary.ContainsKey(otherClass.Name))
{
resultDictionary[otherClass.Name] += otherClass.Number;
}
else
{
resultDictionary.Add(otherClass.Name, otherClass.Number);
}
}
}
While this solution seems to work well, I don’t like it at all.
Is there a more clean way to find this result? Maybe through a nice LINQ query?
As you don’t use any information from the
GeneralClassNameyou can useSelectManyto flatten your list. This flat list ofOtherClassinstances is than grouped by theNameproperty. Finally, the list of groups is transformed into a dictionary with the key of the group (aka theNameproperty) being the key of the new property and the value being the sum of allNumbervalues in that group:This code assumes that
OtherClass.Numberis in fact anintnot astring. This assumption is also used in your sample code with the loop.If this assumption is not correct, change
y.Numbertoint.Parse(CultureInfo.InvariantCulture, y.Number).Note: This will throw an exception if any of the numbers can’t be parsed, so you might want to make sure beforehand that all contain valid numbers.