Skip to main content
 首页 » 编程设计

python之Django OneToOne 字段 self

2024年10月17日36thcjp

如何定义OneToOne 关系到同一个Model?

我有一个名为 Order 的模型,它可以与另一个 Order 配对。现在我想弄清楚如何处理这种关系的模型。

我的想法:

class Order(models.Model): 
    paired_order = models.OneToOneField(self) 

或者:

class Pairing(models.Model): 
    order1 = models.ForeignKey(Order, related_name='pairing') 
    order2 = models.ForeignKey(Order, related_name='pairing') 

你怎么看?哪个更有效率?

我想要配对的简单调用。所以我会做类似的事情:

order.paired_order  

或者:

order.pairing.paired 

我希望这种关系是对称的,所以对于每对订单,我调用相同的东西并得到配对订单。

配对模型会是一个很好的解决方案,因为我可以为这个关系添加额外的信息,但是有一个问题,我必须检测它是哪个顺序,所以我不能调用 order.pairing.order1 因为我不知道我调用的是不是同一个订单。

编辑:

>>> from _app import models 
>>> order1 = models.Order(flight_number="xxx") 
>>> order2 = models.Order(flight_number="yyy", paired_order=order1) 
>>> order1.paired_order.flight_number 

RETURNS 没有对象没有....

问题是,当我将 order1 设置为 order2 的配对订单时,我想要相反方向的相同事物。所以 order1.paired_order = order2 也这样做 order2.paired_order = order1。

请您参考如下方法:

Pairing model would be a good solution because I can add additional information to this relationship.

在这种情况下,您可以为那组“订单”(您称之为配对)建模,并添加一个快捷方式来检索配对的订单。

class OrderPair(models.Model): 
    pass         
    # additional information goes here 
 
 
class Order(models.Model): 
    pair = models.ForeignKey(to="OrderPair", related_name="orders") 
    # you'll have to add custom validation  
    # to make sure that only 2 orders can belong to the same "OrderPair" 
 
    @property 
    def paired_order(self): 
         return self.pair.orders.exclude(id=self.id).first() 

完成这项工作后,您可能还想缓存成对的订单以避免太多查询。在这种情况下,您不需要相关的名称,因此您可以使用 +(Django 中不太明确的东西)。

class Order(models.Model): 
    ... 
    cached_paired_order = models.ForeignKey(to='self', related_name='+') 
 
@property 
def paired_order(self): 
     if self.cached_paired_order: 
          ... 
     else: 
          ...