Skip to main content
 首页 » 编程设计

python之当项目可以出现在多个类别中时,返回出现在单个类别中的项目的 Django 查询集

2025年05月04日35虾米姐

我试图返回一个类别中所有项目的查询集,其中项目可以出现在多个类别中。下面是相关的模型声明以及许多无效的尝试之一。有没有一种方法可以使用 Django 的内置中间表功能来执行此操作,而无需显式声明中间表的模型?

class Category(models.Model): 
    parent = models.ForeignKey('self',null=True,blank=True) 
    name = models.CharField(max_length=150,null=True) 
    description = models.CharField(max_length=255,null=True,blank=True) 
 
    def items(self): 
        curr_category = Category.objects.filter(pk=self.id) 
        items_in_category = curr_category.item__categories_set.all().values('item_id') 
        return Item.objects.filter(pk__in=items_in_category) 
 
    def __unicode__(self): 
        return self.name 
 
 
class Item(models.Model): 
    name = models.TextField(null=True,blank=True) 
    price = models.DecimalField(max_digits=10, decimal_places=2,null=True,blank=True) 
    categories = models.ManyToManyField(Category,null=True) 

请您参考如下方法:

您可以执行此操作的一种方法是在您的 Item 模型上使用自定义 models.Manager。这是理想的,恕我直言,因为这个逻辑并不真正属于您的 Category 模型。如果您想要为 Item 之外的事物分类怎么办?然后,您必须在 Category 上实现更多检索方法,使其膨胀。

class Category(models.Model): 
    parent = models.ForeignKey('self',null=True,blank=True) 
    name = models.CharField(max_length=150,null=True) 
    description = models.CharField(max_length=255,null=True,blank=True) 
 
    def __unicode__(self): 
        return self.name 
 
class ItemManager(models.Manager): 
    def get_for_category(self, category): 
        return self.filter(categories=category) 
 
class Item(models.Model): 
    name = models.TextField(null=True,blank=True) 
    price = models.DecimalField(max_digits=10, decimal_places=2,null=True,blank=True) 
    categories = models.ManyToManyField(Category,null=True) 
    objects = ItemManager() 

然后调用它:

items = Item.objects.get_for_category(category_instance) 

如果您真的想在 Category 方法中执行此操作,那为什么不呢:

class Category(models.Model): 
 
    def items(self): 
        # probably need to import Item model here in order to avoid 
        # circular import reference 
        from myapp.models import Item 
        return Item.objects.filter(categories__id=self.id)