Reputation: 87
Let's say I have such object
public class Example
{
public List<Children> Children {get; set;}
}
public class Children
{
public string Id {get; set;}
public List<Element> {get; set;}
}
public class Element
{
public string Id {get; set;}
}
So I was basically doing
var result1 = example.Children.where(x => x.Children.Any(y => y.Elements.Where(z => z.Id == MyId)));
var actualRes = result1.Elements.Where(x => x.Id = MyId).FirstOrDefault();
But this seems to be very inefficient. Any ideas how to do this properly?
Thanks!
Upvotes: 1
Views: 1132
Reputation: 10704
I was beaten by @Magnetron while writing the test case :-) This answer is a xUnit test for his answer.
using System.Collections.Generic;
using System.Linq;
using Xunit;
namespace XUnitTestProject.StackOverflow
{
public class ElementsTests
{
[Theory]
[MemberData(nameof(GenerateTestData), "~element3~")]
public void Test(Example example, string idInTest)
{
// we should probably use SingleOrDefault instead of FirstOrDefault
// when dealing with instance id
var elementToFind = example.Children
.SelectMany(children => children.Elements)
.FirstOrDefault(element => element.Id.Equals(idInTest));
Assert.NotNull(elementToFind);
Assert.Equal(idInTest, elementToFind.Id);
}
public static TheoryData<Example, string> GenerateTestData(string idInTest) => new()
{
{
new Example()
{
Children = new List<Children>
{
new()
{
Id = "~child1~", Elements = new List<Element>
{
new() {Id = "~element1~"},
new() {Id = "~element2~"}
}
},
new()
{
Id = "~child2~", Elements = new List<Element>
{
new() {Id = idInTest},
new() {Id = "~element4~"}
}
}
}
},
idInTest
}
};
}
}
Upvotes: 1
Reputation: 8543
Your code doesn't compile and have some erros. You can use SelectMany
:
var actualRes = example.Children
.SelectMany(x => x.Elements)
.FirstOrDefault(x => x.Id == MyId);
Code with pre-populated examples:
Example example = new(){
Children = new()
};
for(int i=0; i < 10; i++){
Children c = new(){
Id = i.ToString(),
Elements = new()
};
example.Children.Add(c);
for(int j=0; j < 10; j++){
Element e = new(){
Id=(10*i+j).ToString()
};
c.Elements.Add(e);
}
}
string MyId="23";
var result1 = example.Children
.SelectMany(x => x.Elements)
.FirstOrDefault(x => x.Id == MyId);
Upvotes: 4