4

Suppose I have the following arrays:

List<int[]> numbers = new List<int[]>();
numbers.Add(new int[] { 1, 2, 3 });
numbers.Add(new int[] { 3, 4, 5 });
numbers.Add(new int[] { 5, 6, 7 });

int[] numbersToFind = new int[] { 4, 5, 6 };

I want to find which of the numbers elements contains one/more of the values in numbersToFind, is there an easy way of doing this with LINQ? That is, some code that would return a IEnumerable<int[]> containing an int[]{3,4,5} and int[]{5,6,7} in the above example.

How can this be done?

5 Answers 5

8
numbers.Where(array => array.Any(value => numbersToFind.Contains(value)));
Sign up to request clarification or add additional context in comments.

Comments

6

Try this:

var query = numbers.Where(n => numbersToFind.Any(x => n.Contains(x)));

Here's an alternative approach using the method Enumerable.Intersect:

var query = numbers.Where(n => numbersToFind.Intersect(n).Any());

Comments

4
IEnumerable<int[]> matches = numbers.Where(n => numbersToFind.Intersect(n).Any());

11 Comments

+1 I just added this to my answer, but you beat me by a couple of minutes. I think this is probably better than the top voted answer. :)
Intersect() is going to create a HashMap<int> for each evaluation of the Where lambda. Therefore it will be slower, consume more memory, and create more GC churn. (At least in this limited example.)
@cdhowie: I think it will scale better though - I haven't tested it to be sure. I'm not sure if the example in the OPs question should be understood as a representative example of the sort of query he will be doing or if it has been simplified for the purposes of explanation. I'd guess the latter.
It will not scale. For each number in each source array being considered, a brand new HashMap<int> will be created and populated with the contents of numbersToFind. My example will iterate over every element of numbersToFind until a match is found, where Intersect() is going to construct a HashMap<int> and iterate over EVERY element to build up the hash map, and finally check if it contains the value being considered. I'm sorry, but it's impossible for that to be faster under any circumstances.
If speed is a huge concern, then numbersToFind should itself be a HashMap<int>. Then my example would perform even faster.
|
4

There is a LINQ function Intersect specifically to do this:

numbers.Intersect(numbersToFind)

Comments

1

Try this:

numbers.Where(a => a.Any(s => numbersToFind.Contains(s)));

Good luck!

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.