2010-10-12 3 views
2

Есть ли простой способ, будь то через LINQ или Generics, выяснить, доступны ли элементы в одном списке в другом списке.C# Список <string> «содержит» вопрос

В настоящее время я использую Intersect, чтобы проверить это.

См., Например,

List<string> list1; //{ 5, 4, 1, 3, 9, 8, 6, 7, 2, 0 } 

List<string> list2; //{ 1, 3, 9 } 

list1.Contains(list2) == true 

Заранее спасибо

ответ

8

Метод Intersect предоставит вам все элементы, которые находятся в обоих списках.

E.g.

var inboth = list1.Intersect(list2); 

или если вы просто хотите, чтобы узнать, есть ли какие-либо общие элементы между двумя

if(list1.Intersect(list2).Any()) ... 
+0

Спасибо. Еще один вопрос: что, если все элементы в списке2 должны быть доступны в списке1. Я использую графа. Есть ли способ лучше? – Ganesha

+2

Вы можете использовать 'Except' как' 'if (! List2.Except (list1) .Any()) ...' –

6

Intersect это хороший способ сделать это. Единственный разумный способ это просто перебор его:

list2.All(x => list1.Contains(x)); 

Обратите внимание, что ни один метод будет работать, если, например, list2 является (1 2 2) и list1 является (1 2 3), и вы хотите, чтобы вернуть false. Если вам нужно было это проверить, я бы отсортировал оба списка и спустил их вместе.

2
var list1 = new [] {5, 4, 1, 3, 9, 8, 6, 7, 2}; 
var list2 = new[] {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,5}; 

var hasItems = list1.Where(x => list2.Contains(x)).Any(); 
0

Таким образом, я помещу здесь наивный aproximation, я не уверен, если есть лучший способ

//Checks if list1 is contained in list2 
public bool ContainsList(List<T> list1, List<T> list2) 
{ 

    for (int i = 0; i < list1.Count; i++) 
    { 
    bool inside = false; 

    for (int j = 0; j < list2.Count; j++){ 
     if (list1[i] == list2[j]) 
     inside = true; 
    } 

    //found one in list1 that is not on list2! 
    if (!inside) 
     return false; 
    } 
} 

вычислительная стоимость этого ответа составляет O (н * м), где п и т -длиных списков. Это не LINQ, не лучший способ, но на 100% хорош!

Надеюсь, это поможет!

1

Intersect идеально подходит для этого. Если отчаянный для булева результата, вы могли бы написать метод расширения пользовательского переопределение .Contains()

public static bool WholeyContains<T>(this IEnumerable<T> first, IEnumerable<T> second) 
    { 
     return second.SequenceEqual(first.Intersect(second)); 
    } 
+0

Это не так. 'first' содержит' second', если пересечение является 'second', а не если оно просто не пустое. – mquander

+0

@mquander: Да, согласен. Я пропустил вопрос. Я обновил свой ответ, чтобы убедиться, что второй список полностью совпадает с пересечением. –

1
var a = new int[]{ 1, 2, 3 }; 
var b = new int[] { 1, 2, 3, 4, 5 }; 

bool result = (from numA in a 
       join numB in b 
       on numA equals numB 
       into joined 
       select joined).Count().Equals(a.Count()); // or b.Count() 
Смежные вопросы