Django 的 `Meta` 类和外键的使用

news/2025/1/24 18:48:16/

Django 的 `Meta` 类和外键的使用

      • 1. `Meta` 类的常用选项
      • 2. 外键(ForeignKey)字段的使用
        • 2.1 基本用法
        • 2.2 `ForeignKey` 参数
        • 2.3 外键删除选项(`on_delete`)
      • 3. 外键和查询
        • 3.1 获取作者的所有书籍
        • 3.2 通过书籍查找作者
        • 3.3 使用 `select_related` 优化查询
      • 总结

在 Django 中,Meta 类是模型的一个内部类,用来配置模型的行为和一些数据库选项。通过在模型中定义 Meta 类,你可以控制模型的一些特性,如数据库表名、排序方式、索引、唯一约束等。

1. Meta 类的常用选项

以下是 Meta 类中常用的配置选项:

  • db_table:指定数据库表的名称。如果没有指定,Django 会默认使用模型类名的小写形式作为表名。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:db_table = 'tank_table'  # 指定数据库表名
    
  • ordering:指定模型数据的默认排序方式。它接受一个字段名的列表(可以带负号表示降序)。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:ordering = ['-speed']  # 按照速度降序排列
    
  • verbose_nameverbose_name_plural:用于指定模型的单数和复数形式的可读名称,通常用于 Django 管理后台显示模型名称。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:verbose_name = 'Tank'verbose_name_plural = 'Tanks'
    
  • unique_together:指定多个字段组合成的联合唯一约束。Django 会确保这组字段的组合在数据库中是唯一的。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:unique_together = ['name', 'speed']  # 确保每个name和speed组合是唯一的
    
  • index_together:为多个字段组合创建数据库索引,提高查询效率。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:index_together = ['name', 'speed']  # 为name和speed创建联合索引
    
  • permissions:指定模型的权限。这会在 auth_permission 表中创建自定义权限。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()class Meta:permissions = [("can_drive", "Can drive the tank"),("can_fight", "Can fight with the tank")]
    
  • default_manager_name:设置默认的管理器名称,Django 会在模型类中自动创建 objects 管理器。如果你有多个管理器,可以通过这个选项指定默认的一个。

    python">class Tank(models.Model):name = models.CharField(max_length=100)speed = models.FloatField()active_tanks = models.Manager()  # 自定义管理器class Meta:default_manager_name = 'active_tanks'  # 使用自定义的管理器
    

2. 外键(ForeignKey)字段的使用

Django 的 ForeignKey 字段用于表示模型之间的“一对多”关系。在外键关系中,一个对象可以关联多个对象,常用于表示父子表关系。

2.1 基本用法

ForeignKey 用于表示两个模型之间的外键关系。通常情况下,它会生成一个新的字段,在数据库中存储关联对象的主键(id)。

假设我们有两个模型:AuthorBook。每本书都由一个作者编写,因此我们需要在 Book 模型中添加一个外键字段,指向 Author 模型。

python">from django.db import modelsclass Author(models.Model):name = models.CharField(max_length=100)def __str__(self):return self.nameclass Book(models.Model):title = models.CharField(max_length=200)author = models.ForeignKey(Author, on_delete=models.CASCADE)  # 外键关系,关联到 Author 模型def __str__(self):return self.title
2.2 ForeignKey 参数
  • to:指定外键关联的模型类。可以是另一个模型的类名或字符串(例如 'Author')。
  • on_delete:当关联对象(如作者)被删除时,当前对象(如书籍)该如何处理。常见的选项包括:
    • models.CASCADE:级联删除,删除父对象时删除所有关联的子对象。
    • models.PROTECT:阻止删除父对象,如果该对象仍被引用。
    • models.SET_NULL:将外键字段设置为 NULL(前提是该字段允许为 NULL)。
    • models.SET_DEFAULT:将外键字段设置为默认值。
    • models.SET():可以设置一个特定的值。
  • related_name:为反向关系定义名称。即通过外键模型,可以反向查询到当前模型实例的集合。默认情况下,Django 会使用模型名的小写形式加上 _set 作为反向查询的名称。
  • related_query_name:用于在查询时指定反向关系的名称。
  • null:如果为 True,外键可以为空。
  • blank:如果为 True,字段可以在表单中为空。

例如,添加 related_name 来进行反向查询:

python">class Author(models.Model):name = models.CharField(max_length=100)def __str__(self):return self.nameclass Book(models.Model):title = models.CharField(max_length=200)author = models.ForeignKey(Author, on_delete=models.CASCADE, related_name='books')  # 定义反向查询名称def __str__(self):return self.title

现在,如果你有一个 author 实例,你可以通过 author.books.all() 获取该作者所有的书籍:

python">author = Author.objects.get(id=1)
books_by_author = author.books.all()  # 获取该作者所有的书籍
2.3 外键删除选项(on_delete

当父对象被删除时,Django 会根据你设置的 on_delete 参数来处理外键关系。以下是常用的 on_delete 选项:

  • models.CASCADE:删除父对象时,删除所有引用该父对象的子对象。

    python">author = Author.objects.get(id=1)
    author.delete()  # 删除作者时,所有关联的书籍也会被删除
    
  • models.PROTECT:如果该父对象仍被引用,禁止删除父对象。

    python">author = Author.objects.get(id=1)
    author.delete()  # 如果有书籍关联,删除时会引发异常
    
  • models.SET_NULL:将外键字段设置为 NULL。需要确保外键字段允许 NULL

    python">class Book(models.Model):title = models.CharField(max_length=200)author = models.ForeignKey(Author, on_delete=models.SET_NULL, null=True)
    
  • models.SET_DEFAULT:将外键字段设置为默认值。

    python">class Book(models.Model):title = models.CharField(max_length=200)author = models.ForeignKey(Author, on_delete=models.SET_DEFAULT, default=1)
    
  • models.SET():你可以指定一个函数或值,当父对象删除时,外键字段会设置为指定的值。

    python">class Book(models.Model):title = models.CharField(max_length=200)author = models.ForeignKey(Author, on_delete=models.SET('Unknown Author'))
    

3. 外键和查询

在 Django 中,你可以轻松地使用外键字段进行查询。例如:

3.1 获取作者的所有书籍
python">author = Author.objects.get(id=1)
books = author.books.all()  # 获取该作者的所有书籍
3.2 通过书籍查找作者
python">book = Book.objects.get(id=1)
author = book.author  # 获取书籍的作者
3.3 使用 select_related 优化查询

如果你查询外键字段时,经常会发起额外的数据库查询。你可以使用 select_related 来一次性加载相关的外键数据,减少查询次数。

python">books = Book.objects.select_related('author').all()  # 一次性查询所有书籍及其对应的作者

总结

  • Meta 类用于在模型中配置数据库表的选项,如表名、排序、索引等。
  • 外键字段(ForeignKey)用于表示模型之间的“一对多

http://www.ppmy.cn/news/1565851.html

相关文章

iOS UIScrollView的一个特性

1如果UIScrollView 的contentSize.height > scrollView.bounds.size.height - scrollView.contentInset.top - scrollView.contentInset.bottom , 则scrollView就可以滚动,否则无法滚动 并且最大的滚动范围就是 contentSize.height - ( s…

如何有效使用Python爬虫将网页数据存储到Word文档

在数据处理和文档自动化生成的场景中,Python爬虫技术结合文档操作库(如python-docx)可以实现高效的数据抓取和文档生成。本文将详细介绍如何使用Python爬虫技术抓取网页数据,并将其存储到Word文档中,同时提供完整的代码…

ES filter和post_filter的区别

ES filter和post_filter的区别 在Elasticsearch中,过滤搜索的结果是我们经常要做的事。在我刚开始接触 Elasticsearch,我就了解到有两种可以过滤搜索结果的方法。当时还不是很明白,为什么有的地方用 filter,而有的地方需要使用到…

【负载均衡式在线OJ】加载题目信息(文件版)

目录 如何读取文件 -- 常见流程 代码 如何读取文件 -- 常见流程 在C中使用 std::ifstream来打开文件流是一个常见的操作,用于创建一个输入文件流,并尝试打开名为 question_list的文件。if (!in.is_open()):检查文件是否成功打开。如果文件未…

Windows安装Miniconda和PySide6以及配置PyCharm

目录 1. 选择Miniconda 2. 下载Miniconda 3. 安装Miniconda 4. 在base环境下创建pyside6环境 5. 安装pyside6环境 6. 配置PyCharm环境 7. 运行第一个程序效果 1. 选择Miniconda 选择Miniconda而没有选择Anaconda,是因为它是一个更小的Anaconda发行版&#x…

MySQL可直接使用的查询表的列信息

文章目录 背景实现方案模板SQL如何查询列如何转大写如何获取字符位置如何拼接字段 SQL适用场景 背景 最近产品找来,想让帮忙出下表的信息,字段驼峰展示,每张表信息show create table全部展示,再逐个粘贴,有点太耗费时…

算力需求大爆发,谁是“大推手”?

大约5亿年前,地球迎来了物种的突然大爆发,标志着生物进化除了缓慢渐变,还可能以跳跃的方式进行。 同样,人工智能在经历70余年曲折发展之后,也处于一个极为关键的时刻,在模型、数据、算力等各项基础技术多年…

【Leetcode 热题 100】279. 完全平方数

问题背景 给你一个整数 n n n,返回 和为 n n n 的完全平方数的最少数量 。 完全平方数 是一个整数,其值等于另一个整数的平方;换句话说,其值等于一个整数自乘的积。例如, 1 , 4 , 9 1,4,9 1,4,9 和 16 16 16 都是完…