EF Многие ко многим выбирают пересечение

1

Я пытаюсь внедрить систему тегов с каркасом сущностей С#. Я не могу получить запрос, требуемый для случая, когда ожидаются два или более тега для возврата результата. У меня много отношений (только FKs, DB), и я пытаюсь получить объект, когда все выбранные теги существуют. Object - LookupTable - Атрибуты. Я разбираю выбранные теги в списке, а затем пытаюсь получить только те объекты, для которых присутствуют все теги в этом списке. По-видимому, это приводит к тому, что я ожидаю от оператора "Любой", а не от "Все".

List<string> intersectTags = new List<string>();

foreach (object i in ef.objects.Where(o => o.Attributes.All(attribute =>
intersectTags.Contains(attribute.AttributeNK))))

Обновление. Также необходимо получить экземпляры, где ef.Object имеет больше тегов, чем intersectTags. Фильтрация для экземпляров, где intersectTags является подмножеством Object.Attributes.

Теги:
entity-framework-6

2 ответа

1
Лучший ответ

Ваш код не работает, если ваши атрибуты являются подмножеством выбранных тегов.

Если вы ищете совпадение, когда intersectTags является подмножеством o.Attributes, попробуйте изменить регистр.

К сожалению, Linq to Entity не поддерживает такой синтаксис, нам нужен ToList() для загрузки объектов и выполнения Linq To Objects.

Он должен работать, но есть последствия для производительности (я опубликую обновление, если у меня есть лучшее решение):

List<string> intersectTags = new List<string>();

foreach (object i in ef.objects.ToList().Where(intersectTags.All(tags =>
o.Attributes.Any(attribute => attribute.AttributeNK == tags))))
  • 0
    Отлично, спасибо! В этом есть смысл, когда я вижу это ... достаточно новое для EF, поэтому я сомневаюсь в себе в других областях вместо того, чтобы смотреть на возможные проблемы при сравнении. Также изменено на> =, чтобы ничего не пропустить, но избежать выявленной вами проблемы подмножества.
  • 0
    Ну, это решает одну проблему и вводит другую ... как я могу сопоставить, когда o.Attributes имеет больше тегов, чем intersectTags? В этом случае я ищу соответствие, когда intersectTags является подмножеством o.Attributes.
Показать ещё 6 комментариев
0

Я не знаю, хорошо ли я понял, если так, я могу дать решение в простом SQL. Вы должны искать все записи, содержащие один из запрошенных тегов, а затем группировать их с помощью productId с условием HAVING COUNT равным количеству передаваемых вами тегов.

SELECT ProductId FROM ProductTag
WHERE  TagId IN (2,3,4)
GROUP BY ProductId
HAVING COUNT(*) = 3

Вот демо:

http://sqlfiddle.com/#!3/dd4023/3

Извините, в настоящее время я не могу дать вам реализацию в EF (у меня нет Visual Studio), я сделал что-то подобное для LINQ TO SQL и использует класс PredicateBuilder, вы можете найти его здесь:

http://www.codeproject.com/Articles/36178/How-to-manage-product-options-with-different-price

Paolo

Ещё вопросы

Сообщество Overcoder
Наверх
Меню