Django模型层基本概念

2018-09-16  本文已影响25人  Ghibli_Someday

所有Django模型继承<django.db.models.Model>类
通过类属性定义模型字段,如:models.XXField
通过模型类中的Meta子类定义模型元数据(非字段的其他数据),如:数据库表名,数据默认排序方式

常见Meta类属性:

普通字段是指模型类中除外键关系外的数据字段属性,提供以下信息:

常用普通字段:

常用字段参数:

基本查询:

Django通过模型的objects对象实现模型数据查询
过滤器:

X.objects.filter(pub_date__year=2015)
X.objects.filter(pub_date__year=2015).exclude(pub_date__month=1)

PS:两者可以结合使用

Django独特的字段查询(filed lookup):字段名称__谓词(双下滑线)
字段查询谓词:X.objects.filter.

数据保存与删除:
定义了统一的save(),用于完成模型的 Insert 和 Update 操作
定义了delete()用于删除记录

关系操作:

利用数据表之间的关系进行数据建模和业务开发是关系数据库最主要的功能
1、一对一关系(OneToOneField)

from django.db import models
class Account(models.Model):
    user_name = models.CharField(max_lenght=80)
    password = models.CharField(max_length=255)
    reg_date = models.DateField()
    
    # __unicode__()函数用于定义模型的显示字符串
    def __unicode__(self):
        return 'Account: %s' % self.user_name
   
class Contact(models.Model):
    # on_delete参数定义当被关联模型的记录被删除时本模型的记录如何处理
    # models.CASCADE用于定义本记录也被删除
    account = models.OneToOneField(Account, on_delete=models.CASCADE, primary_key=True)
    zip_code = models.CharField(max_length=10)
    address = models.CharField(max_length=80)
    mobile = model.CharField(max_length=20)
    
    def __unicode__(self):
        return '%s %s' % (self.account.user_name, mobile)

2、一对多关系

from django.db import models
class Account(models.Model):
    user_name = models.CharField(max_lenght=80)
    password = models.CharField(max_length=255)
    reg_date = models.DateField()
    
    def __unicode__(self):
        return 'Account: %s' % self.user_name
   
class Contact(models.Model):
    account = models.ForeignKey(Account, on_delete=models.CASCADE, primary_key=True)
    zip_code = models.CharField(max_length=10)
    address = models.CharField(max_length=80)
    mobile = model.CharField(max_length=20)
    
    def __unicode__(self):
        return '%s %s' % (self.account.user_name, mobile)

3、多对多关系

from django.db import models
class Account(models.Model):
    user_name = models.CharField(max_lenght=80)
    password = models.CharField(max_length=255)
    reg_date = models.DateField()
    
    def __unicode__(self):
        return 'Account: %s' % self.user_name
   
class Contact(models.Model):
    account = models.ManyToManyField(Account)
    zip_code = models.CharField(max_length=10)
    address = models.CharField(max_length=80)
    mobile = model.CharField(max_length=20)
    
    def __unicode__(self):
        return '%s %s' % (self.account.user_name, mobile)

面向对象ORM:

Django支持三种风格的模型继承
1、抽象类继承:父类继承自models.Model,但不会在底层数据库生成相应的数据表

from django.db import models
class MessageBase(models.Model):
    id = models.AutoField()
    content = models.CharField(max_length=100)
    user_name = models.CharField(max_length=80)
    pub_date = models.DateField()
    
    class Meta:
        abstract = True
class Moment(MessageBase):
    headline = models.CharField(max_length=50)
    
LEVELS = (
    ('1', 'Very good')
    ('2', 'Good')
    ('3', 'Normal')
    ('4', 'Bad')
)
class Coment(MessageBase):
    level = models.CharField(max_length=1, choices=LEVELS)

迁移数据后,会定义两个数据表:
数据表 Moment:有id、content、user_name、pub_date、headline
数据表 Comment:有id、content、user_name、pub_date、level

2、多表继承:每个模型都在数据库中生成相应的数据表管理数据,父类中的字段不会重复地在多个子类的相关数据表中定义,从这个意义讲,多表继承才是真正的面向对象的ORM技术

from django.db import models
class MessageBase(models.Model):
    id = models.AutoField()
    content = models.CharField(max_length=100)
    user_name = models.CharField(max_length=80)
    pub_date = models.DateField()
    
class Moment(MessageBase):
    headline = models.CharField(max_length=50)
class Coment(MessageBase):
    level = models.CharField(max_length=1, choices=LEVELS)

迁移数据后,会定义三个数据表:
数据表 Moment:有id、headline
数据表 Comment:有id、level
数据表 MessageBase:有id、content、user_name、pub_date
PS:在子类实例中可以通过小写的父类的名字可以引用父类的实力

m1 = Moment(user_name='Terry', headline='Hello World')
print m1.messagebase.user_name

3、代理模型继承:父类用于在底层数据库中管理数据表,而子类不定义数据列,只定义查询数据集的排序方式等元数据

from django.db import models
class Moment(models.Model):
    id = models.AutoField()
    headline = models.CharField(max_length=50)
    content = models.CharField(max_length=100)
    user_name = models.CharField(max_length=80)
    pub_date = models.DateField()
    
class OrderedMoment(Moment):
    class Meta:
        proxy = True
        ordering = ['-pub_date']

使用代理模型继承的原因是子类中新的特性不会影响父类模型及其已有代码的行为

上一篇下一篇

猜你喜欢

热点阅读