Django:在mixin中覆盖save方法有意义吗? [英] Django : Does it make sense to override save method in a mixin?

查看:67
本文介绍了Django:在mixin中覆盖save方法有意义吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我问自己在 mixin 中覆盖 save 方法是否有意义.

I ask myself if it make sense to override save method in a mixin.

在我的项目中,出于充分的理由,我在多个模型中覆盖了 save 方法.首先,我必须创建一个从 models.Model 继承的自定义模型类.无论从语义上讲,我所做的是为类赋予一个角色(而不是自己定义一个对象),这就是为什么我认为最好编写一个 mixin.另一个原因是因为我们可能在不久的将来使用多重继承.另一方面,覆盖保存方法中的这一行:

In my project I have, for good reasons, to override the save method in several models. At first, I have to create a custom model class which inherit from models.Model. However semantically, what I am doing is giving a role to a class (rather than defining an object in its own right), that's why I think it's better to write a mixin. An other reason is because we may use multiple inheritance in near future. On the over hand, this line in overriden save method :

super(MyMixin, self).save(*args, **kwargs)

没有意义,因为它只能与 django.db.models.Model 类一起使用.

does not make sens as it can only be used with a django.db.models.Model class.

class MyMixin(object):

    def save(self, *args, **kwargs):
        ...
        super(MyMixin, self).save(*args, **kwargs)
        ...

你能帮我决定最佳选择吗?(混合或自定义模型)

Could you help me decide the best choice ? (Mixin or custom model)

推荐答案

mro(方法解析顺序)的工作方式,两种方法都是完全有效的.抽象模型案例非常简单:你有一个单一的继承链,每次调用 super 都会在链中的下一个类上调用.所以如果你有:

The way the mro (method resolution order) works, both methods are perfectly valid. The abstract model case is quite simple: you have a single inheritance chain, and each call to super is called on the next class up in the chain. So if you have:

class MyBaseModel(models.Model):
    def save(self, *args, **kwargs):
        super().save(*args, **kwargs)

class MyModel(MyBaseModel):
    def save(self, *args, **kwargs):
        super().save(*args, **kwargs)

MyModel 中的调用将传播到 MyBaseModelMyBaseModel 中的调用将传播到 models.Model>.

The call in MyModel will propogate to MyBaseModel, and the call in MyBaseModel will propogate to models.Model.

对于多重继承,继承链略有不同.继承链中的第一个类是定义的第一个基类.所以如果你有 class MyModel(MyMixin, models.Model)MyMixin 将是第一个向上的类.接下来,当在 MyMixin 中调用 super() 时(使用 MyModel 实例),它会寻找 MyMixin<的兄弟/代码> 类.这意味着下一个要调用的方法是 models.Model 上的 save 方法.

With multiple inheritance, the inheritance chain is slightly different. The first class upwards in the inheritance chain is the first base class defined. So if you have class MyModel(MyMixin, models.Model), MyMixin will be the first class upwards. Next, when super() is called in MyMixin (with a MyModel instance), it will look for siblings of the MyMixin class. That means that the next method to be called is the save method on models.Model.

考虑到这一点,使用 mixin 覆盖保存方法是完全没问题的.在这两种情况下,将首先调用 MyModel 保存方法,然后是混合/抽象模型的保存方法,最后是 models.Model 保存方法.

Considering this, it is perfectly fine to use a mixin to override the save methods. In both cases, the MyModel save method will be called first, then the mixin/abstract model's save method, and finally the models.Model save method.

注意:

这是对在此特定情况下起作用的方法解析顺序的简化说明.确定顺序的实际算法是 C3 线性化算法.可以在此处找到完整的说明.

This is a simplified explanation of the method resolution order that works in this specific case. The actual algorithm for determining the order is the C3 linearization algorithm. A complete explanation can be found here.

这篇关于Django:在mixin中覆盖save方法有意义吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆