Django 多对多比较

3 投票
2 回答
3853 浏览
提问于 2025-04-16 13:04

有没有办法比较两个不同模型之间的多对多关系?

我有一个叫做“Days”的模型,还有另外两个模型:

  • Ticket(这个模型和Days有多对多的关系)
  • Check(这个模型也和Days有多对多的关系)

我可以用两个循环来实现这个功能,但这样看起来不太好,也不太容易理解。

2 个回答

0

我不太明白你想要什么。你是想获取所有与Checkday相同的Ticket吗?

class Day(models.Model):
    # don't know what fields exist..
    date = models.DateField(...)

check = Check.objects.all()[0]
check_dates = [day.date for day in check.days.all()]
tickets_for_check = Ticket.objects.filter(days__date__in=check_dates)

这假设了一个日期为'x'的Ticket-Day实例和一个日期为'x'的Check-Day实例有不同的ID。简单来说,同一天的实例会因为来源模型不同而被视为不同的实例。

如果能提供一个示例输出和你的模型描述就更好了。不过这段代码应该能解决你的问题。哦,注意在表中根据某个值进行比较而不是ID的话,性能会很差。要么重新考虑你的数据模型,就像@Thomas建议的那样,要么在你的Day模型的date属性上创建一个索引。

1

如果我理解你的问题没错,你可以通过在Ticket和Check模型中的多对多关系声明里定义相关名称,来实现你想要的功能,然后比较查询结果。

举个例子:

class Day(models.Model):
    day = models.DateField()

class Ticket(models.Model):
    ticket_name = models.CharField()
    days = models.ManyToMany(Day, related_name="tickets")

class Check(models.Model):
    check_name = models.CharField()
    days = models.ManyToMany(Day, related_name="checks")

现在,如果你想找到某一天的所有票和检查来进行比较,你可以这样做:

date = datetime.date(day=1, month=1, year=2000)
day = Day.objects.select_related().get(day=date)

ts = day.tickets
cs = day.checks

如果你想要与票名为ticket的Ticket相关的所有检查:

checks_for_ticket = Check.objects.filter(days__tickets__ticket_name="tickets")

如果你想要与检查名为check的Check相关的所有票:

tickets_for_check = Ticket.objects.filter(days__checks__check_name="check")

撰写回答