亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Django中多對(duì)多關(guān)系三種定義方式

 更新時(shí)間:2025年06月27日 08:50:33   作者:Adolf_1993  
Django 中的多對(duì)多關(guān)系可以通過(guò)三種方式定義,它們?cè)谑褂帽憬菪院涂蓴U(kuò)展性上各有差異,下面就來(lái)介紹一下如何實(shí)現(xiàn),感興趣的可以了解一下

Django 中的多對(duì)多關(guān)系(ManyToManyField)可以通過(guò) 三種方式定義,它們?cè)谑褂帽憬菪院涂蓴U(kuò)展性上各有差異。以下是完整總結(jié) ? 并注明每種方式中哪些方法不可用

? 方式一:默認(rèn)方式(Django 自動(dòng)創(chuàng)建中間表)

? 特點(diǎn):

  • 最常用、最方便
  • Django 自動(dòng)生成中間表
  • 不支持自定義字段

? 示例:

class Author(models.Model):
    name = models.CharField(max_length=100)

class Book(models.Model):
    title = models.CharField(max_length=100)
    authors = models.ManyToManyField(Author)

? 可用方法:

方法可用?說(shuō)明
.add(obj)?添加關(guān)聯(lián)
.remove(obj)?移除關(guān)聯(lián)
.set([obj1, obj2])?重新設(shè)置關(guān)聯(lián)
.clear()?清除所有關(guān)聯(lián)
.all()?查詢(xún)所有關(guān)聯(lián)對(duì)象

? 方式二:使用 through 自定義中間表(推薦用于需要額外字段的情況)

? 特點(diǎn):

  • 中間模型可添加自定義字段(如創(chuàng)建時(shí)間、角色等)
  • 更靈活,但略復(fù)雜

? 示例:

class Author(models.Model):
    name = models.CharField(max_length=100)

class Book(models.Model):
    title = models.CharField(max_length=100)
    authors = models.ManyToManyField(
                            Author, 
                            through="BookAuthor", 
                            through_fields=("book", "author")
)

class BookAuthor(models.Model):
    book = models.ForeignKey(Book, on_delete=models.CASCADE)
    author = models.ForeignKey(Author, on_delete=models.CASCADE)
    added_at = models.DateTimeField(auto_now_add=True)

? 禁用方法:

方法可用?說(shuō)明
.add(obj)?被禁用,Django 不知道如何填中間表
.remove(obj)?? 同上
.set([obj1, obj2])?? 同上
.clear()?? 同上
.all()?查詢(xún)?nèi)匀豢捎?/td>

? 正確操作方式:

使用中間模型手動(dòng)添加:

BookAuthor.objects.create(book=book, author=author)

? 方式三:完全手動(dòng)中間表,無(wú) ManyToManyField

? 特點(diǎn):

  • 不定義 ManyToManyField
  • 所有關(guān)系自己通過(guò)中間表查詢(xún)管理
  • 最靈活,但也最復(fù)雜,不推薦日常使用

? 示例:

class Author(models.Model):
    name = models.CharField(max_length=100)

class Book(models.Model):
    title = models.CharField(max_length=100)

class BookAuthor(models.Model):
    book = models.ForeignKey(Book, on_delete=models.CASCADE)
    author = models.ForeignKey(Author, on_delete=models.CASCADE)
    added_at = models.DateTimeField(auto_now_add=True)

? 所有 .authors.xxx 都不可用

方法可用?說(shuō)明
.add() / .remove() / 等?沒(méi)有 ManyToManyField 字段
.all()?也不能直接訪(fǎng)問(wèn) .authors.all()
查詢(xún)方式?需手動(dòng)通過(guò)中間表查詢(xún)
# 查詢(xún)一本書(shū)的所有作者
BookAuthor.objects.filter(book=book).select_related("author")

# 查詢(xún)一個(gè)作者的所有書(shū)
BookAuthor.objects.filter(author=author).select_related("book")

? 總結(jié)對(duì)比表

方式是否有中間模型是否能添加中間字段快捷方法(add/remove/set)推薦用途
默認(rèn) ManyToManyField?(Django 自動(dòng))?? 可用簡(jiǎn)單多對(duì)多關(guān)系
ManyToManyField + through??? 被禁用多對(duì)多且需附加字段場(chǎng)景
完全手動(dòng)中間模型??? 全部禁用高度自定義業(yè)務(wù)、底層控制場(chǎng)景

在 Django 中,ManyToManyField 提供了一套專(zhuān)門(mén)用于 增刪改查(CRUD) 的方法,用于操作模型之間的多對(duì)多關(guān)系。以下是完整的 CRUD 方法總結(jié)(適用于未使用 through 中間模型的情況):

? Django 多對(duì)多的 CRUD 方法匯總

假設(shè)模型如下:

class Author(models.Model):
    name = models.CharField(max_length=100)

class Book(models.Model):
    title = models.CharField(max_length=100)
    authors = models.ManyToManyField(Author)

? 1. C:創(chuàng)建關(guān)系(Create)

? 方法一:創(chuàng)建對(duì)象后添加關(guān)聯(lián)

book = Book.objects.create(title="Python入門(mén)")
author = Author.objects.create(name="張三")

book.authors.add(author)  # 添加關(guān)聯(lián)關(guān)系

? 方法二:一次添加多個(gè)對(duì)象

book.authors.add(author1, author2, author3)

? 2. R:查詢(xún)關(guān)系(Read)

# 查詢(xún)某本書(shū)的所有作者
book.authors.all()

# 查詢(xún)某個(gè)作者參與的所有書(shū)(反向查詢(xún))
author.book_set.all()

# 如果設(shè)置了 related_name="books",可以用:
author.books.all()

? 3. U:更新關(guān)系(Update)

? 重新設(shè)置關(guān)系(會(huì)先清空原有關(guān)系再添加新關(guān)系)

book.authors.set([author1, author2])  # 只保留這兩個(gè)作者

? 4. D:刪除關(guān)系(Delete)

? 刪除指定的某個(gè)或多個(gè)關(guān)系:

book.authors.remove(author1)
book.authors.remove(author1, author2)

? 清除所有關(guān)系:

book.authors.clear()

? 使用限制說(shuō)明(重要)

方法是否可用條件說(shuō)明
.add()?不能用于通過(guò) through 自定義中間模型
.remove()?同上
.clear()?同上
.set()?同上
.all()?始終可用

? 如果你在 ManyToManyField 中使用了 through="XXX",上述 .add() 等方法會(huì)全部失效,必須手動(dòng)操作中間模型。

? 5. 示例:完整流程演示

# 添加關(guān)系
book = Book.objects.create(title="FastAPI進(jìn)階")
author1 = Author.objects.create(name="Alice")
author2 = Author.objects.create(name="Bob")
book.authors.add(author1, author2)

# 查詢(xún)關(guān)系
for author in book.authors.all():
    print(author.name)

# 更新關(guān)系
book.authors.set([author2])  # 現(xiàn)在只有 Bob

# 刪除單個(gè)關(guān)系
book.authors.remove(author2)

# 清空所有關(guān)系
book.authors.clear()

到此這篇關(guān)于Django中多對(duì)多關(guān)系三種定義方式的文章就介紹到這了,更多相關(guān)Django 多對(duì)多關(guān)系創(chuàng)建內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家! 

相關(guān)文章

最新評(píng)論