1.应用场景:比如一个文章的分类中可以含有多篇文章 ,但是一篇文章只能属于一个分类,这就是典型的一对多关系。
2.实现方式 :一对多或者是多对一,都是通过“ForeignKey”来实现的,在这里以文章和分类的案例进行讲解。
articleAPP中models.py中定义模型,示例代码如下:
from django.db import models
class Article(models.Model):
title = models.CharField(max_length=100)
content = models.TextField()
# 可以指定默认值,同样也可以指定null=True,因为默认情况下,null=False
# 可以修改models.name_set名字,通过Foreign_key()中的属性,related_name
author = models.ForeignKey('frontuser.User', on_delete=models.CASCADE, default=1)
# 应用不同app中定义的模型,可以通过指定‘app名.模型名’
category = models.ForeignKey('frontuser.Category', on_delete=models.CASCADE, default=1, related_name='articles')
def __str__(self):
return "<(Article: (id: %s, title: %s, content: %s, author: %s, category: %s))>" % \
(self.id, self.title, self.content, self.author, self.category)
frontuserAPP中models.py文件中示例代码如下:
from django.db import models
class User(models.Model):
name = models.CharField(max_length=20, default=1)
# 重写类的__str__(str)方法,在调用类的时候就会执行__str__(self)方法。
def __str__(self):
return "<(User: (id: %s, name: %s))>" % (self.id, self.name)
class Category(models.Model):
name = models.CharField(max_length=100, default=1)
# 重写类的__str__(self)方法
def __str__(self):
return "<(Category: (id: %s, name: %s))>" % (self.id, self.name)
在article中的views.py文件中,示例代码如下:
from django.shortcuts import render
from django.http import HttpResponse
from .models import Article
from frontuser.models import User,Category
def index(request):
# 添加用户数据信息
# user = User(name='小蚂蚁')
# user.save()
#
# # 2.category数据信息添加
# category = Category(name='国际新闻')
# category.save()
#
# # 3.article信息添加
# article = Article(title='美国大选', content='女士们,先生们..')
# article.save()
return HttpResponse("success")
def one_to_many(request):
# 1.添加一条数据,表与表之间的关系一对多
# article = Article(title='习大大慰问', content='同志们好')
# user = User.objects.first()
# category = Category.objects.first()
#
# article.author = user
# article.category = category
# article.save()
# 2.修改文章信息
# article = Article.objects.get(title='美国大选')
# category = Category.objects.get(name='国际新闻')
# article.category = category
# article.save()
# 3.查找某个分类下所有的文章
# 如果一个模型被其他的模型进行引用了,就会为这个模型添加一个方法为:
# 被引用模型名小写字母_set,这个方法的使用和objects方法很相似
# category = Category.objects.first()
# # 得出的信息为RelateManager
# article = category.article_set.first()
# # 重写所有模型的__str__(self)方法
# print(article)
# 4.通过另外一种方法,将某一篇文章添加到某个分类中
# 同样,被引用的模型下的models.name_set方法可以被重新定义为一个新的名字
# 在模型中的ForeignKey()中有一个参数为 related_name,可以通过这个参数来更改
# category = Category.objects.first()
# article = Article(title='阿里巴巴', content='扫福活动')
# article.author = User.objects.first()
# article.save()
#
# # 将文章添加到分类中
# category.articles.add(article)
# category.save()
# 5.在我们的对象还没有 保存,我们可以通过指定bluk=False,来让Django底层去保存
# 再添加一篇文章,示例
category = Category.objects.get(pk=3)
article = Article(title='特朗普今日活动', content='保镖...')
article.author = User.objects.get(pk=3)
category.articles.add(article, bulk=False)
return HttpResponse("添加成功")
*使用“bulk=False”,那么Django就会自动保存article,而不需要在添加到category之前 先保存article。或者是另外一种解决方式是,在添加到"category.article_set"中之前,先将“article”保存到数据库中,但是此时如果 “article.category”不能为空,那么就会产生一种死循环了,即article没有 "category"不能进行保存,而将article添加到"category.article_set"中,有需要article之前是已经存储到数据库中的。
查看数据库中article表中的数据信息: