LINQ zwraca pozycje na liście, które pasują do dowolnych nazw (string) na innej liście
Mam 2 listy. 1 to kolekcja produktów. A drugi to kolekcja produktów w sklepie.
Muszę być w stanie zwrócić wszystkie produkty, jeśli nazwy pasują do nazw produktów.
Mam to, ale nie działa. Jakieś pomysły? var products = shopProducts.Where(p => p.Name.Any(listOfProducts.
Select(l => l.Name).ToList())).ToList();
Muszę powiedzieć, że daj mi wszystkie produkty, gdzie nazwa istnieje na drugiej liście.
5 answers
var products = shopProducts.Where(p => listOfProducts.Any(l => p.Name == l.Name))
.ToList();
Dla LINQ-to-Objects, jeśli listOfProducts
zawiera wiele elementów, to może uzyskać lepszą wydajność, jeśli utworzysz HashSet<T>
zawierającą wszystkie wymagane nazwy i użyjesz jej w zapytaniu. HashSet<T>
ma wydajność o(1) w porównaniu do O(n) dla dowolnego IEnumerable<T>
.
var names = new HashSet<string>(listOfProducts.Select(p => p.Name));
var products = shopProducts.Where(p => names.Contains(p.Name))
.ToList();
Dla LINQ-to-SQL, oczekiwałbym (hope?), że dostawca może zoptymalizować wygenerowany SQL automatycznie bez konieczności ręcznego dostosowywania zapytania.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-28 09:09:25
Możesz użyć join, na przykład:
var q = from sp in shopProducts
join p in listOfProducts on sp.Name equals p.Name
select sp;
Pełniejszy przewodnik po join znajduje się tutaj .
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-28 08:53:07
Można utworzyć IEqualityComparer<T>
, który mówi, że produkty o równych nazwach są równe.
class ProductNameEqulity : IEqualityComparer<Product>
{
public bool Equals(Product p1, Product p2)
{
return p1.Name == p2.Name
}
public int GetHashCode(Product product)
{
return product.Name.GetHashCode();
}
}
Następnie możesz użyć tego w metodzie rozszerzenia Intersect
.
var products = shopProducts.Intersect(listOfProducts, new ProductNameEquality());
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-28 08:57:27
Spróbuj tego proszę
var products = shopProducts.Where(m=> listOfProducts.Select(l=>l.Name).ToList().Contains(m=>m.Name));
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-28 08:49:53
var products = shopProducts
.Where(shopProduct =>
listOfProducts.Any(p => shopProduct.Name == p.Name))
.ToList();
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-28 08:51:54