Django 快速多对多过滤

Django fast Many-To-Many filtering

假设我有两个模型:类别和产品

class Category(models.Model):
    name = models.CharField(max_length='255')
    parent = models.ForeignKey("self", on_delete=models.CASCADE, null=True, related_name='children', related_query_name='child')

class Product(models.Model):
    name = models.CharField(max_length='255')
    category = models.ManyToManyField(Category)

我的数据库中有大约 600 万个产品和 12k 个类别。每个产品都有多个类别。我想按 category_id:

筛选产品
    categories = [1, 5, 6, 7, ....]
    products = Product.objects.filter(category__pk__in=categories)

在 MtM 字段上过滤可以 return 重复,所以我需要 distinct()。但是对于 distic fitering 最多可能需要 15 秒。有什么方法可以更快地获得不同的产品吗?我将不胜感激

你可以试试从另一边接近它。从类别中获取产品的id,然后通过id过滤产品。在我的测试中,我得到了 60% 的改进。

class Product(models.Model):
    name = models.CharField(max_length='255')
    category = models.ManyToManyField(Category, related_name="products")

product_ids = Category.objects.filter(id__in=categories).values_list("products__id", flat=True).distinct()
products = Product.objects.filter(id__in=product_ids)