Как получить похожие проекты на основе тегов в Django - PullRequest
0 голосов
/ 13 октября 2011

В моем приложении есть модели Project и Tag, между которыми существует отношение многие ко многим.На странице каждого проекта я хочу перечислить 3 дополнительных проекта, которые имеют больше общего с ним тегов.Как я могу выполнить этот запрос?

class Tag(models.Model):
  name = models.CharField(max_length=300)

class Project(models.Model):
  name = models.CharField(max_length=300)
  ...
  tags = models.ManyToManyField(Tag)

1 Ответ

4 голосов
/ 13 октября 2011

Можно упаковать все в одну строку:

Project.objects.filter(tags__in=current_project.tags.all()).annotate(Count('name')).order_by('-name__count')[:3]

Или, разбито на шаги:

tags = current_project.tags.all()
matches = Project.objects.filter(tags__in=tags).annotate(Count('name'))
results = matches.order_by('-name__count')[:3]

Логика выглядит следующим образом:

  1. current_project - это экземпляр проекта, для которого вы хотите установить отношения.
  2. filter выбирает все проекты, теги которых совпадают с текущим проектом.
  3. annotate добавляет переменную к возвращаемым значениям, которая подсчитывает количество похожих имен. Поскольку проекты, соответствующие нескольким тегам, возвращаются несколько раз, это значение указывает на количество совпадений.
  4. Результаты отсортированы по аннотированной переменной name__count. Чтобы получить первые 3 результата, список ограничен с помощью [:3].
...