Django 【补充】ORM多对多正向查询

一、多对多的正反向查询

class Class(models.Model):
    name = models.CharField(max_length=32,verbose_name="班级名")
    course = models.CharField(verbose_name="课程",max_length=32)
    def __str__(self):
        return self.name

class Teacher(models.Model):
    name = models.CharField(max_length=23,verbose_name="姓名")
    classes = models.ManyToManyField(verbose_name="所属班级",to="Class")
    def __str__(self):
        return self.name

题目1:查找娜娜老师所带的班级

        # 方式一:基于对象的查找
        obj = models.Teacher.objects.filter(name="娜娜").first()
        print(obj.classes.all())
        print("娜娜老师带的班级",obj.classes.values("name"))
        # 方式二:基于双下划线的查找
        obj_cls = models.Teacher.objects.filter(name="娜娜").values("classes__name")
        print("娜娜老师带的班级",obj_cls)

注意:要说明的是多对多的查询用.all,,查单个的时候用.values或者values_list,不要用obj.classes.name,,这样查到的会是None,反向查询也是如此。我就是犯了这样的错,引以为戒。。

总结:不管是一对多,还是多对多,要是查询多得一方就得用all()

运行结果截图:

Django 【补充】ORM多对多正向查询

表结构:

from django.db import models

# Create your models here.
# 一个学生有一个班级,一个班级可以有好多学生,所以是
# 一对多的关系,关联字段放在多的一方
class Student(models.Model):
    name = models.CharField(max_length=32,verbose_name="姓名")
    age = models.IntegerField(verbose_name="年龄")
    classes = models.ForeignKey(to="Class",verbose_name="所属班级")
    def __str__(self):
        return self.name

class Class(models.Model):
    name = models.CharField(max_length=32,verbose_name="班级名")
    course = models.CharField(verbose_name="课程",max_length=32)
    def __str__(self):
        return self.name

class Teacher(models.Model):
    name = models.CharField(max_length=23,verbose_name="姓名")
    classes = models.ManyToManyField(verbose_name="所属班级",to="Class")
    def __str__(self):
        return self.name

2、查询海燕在那个班级

  # 方式一:
    print("海燕所在的班级",models.Student.objects.filter(name="海燕").values("classes__name"))
    # 方式二:
    obj_cls = models.Student.objects.filter(name="海燕").first()
    print("海燕所在的班级",obj_cls.classes.name)

3、查询海燕所在班的老师的姓名

  print("海燕所在班的老师的姓名",models.Student.objects.filter(name="海燕").values("classes__teacher__name"))

4、查询软件测试151班的所有学生的姓名

 print("软件测试151班的所有学生的姓名",models.Class.objects.filter(name="软件测试151").values("student__name"))
 obj = models.Class.objects.filter(name="软件测试151").first()
 # print("软件测试151班的所有学生的姓名",obj.student_set.name)  #这样打印的结果是None
 print("软件测试151班的所有学生的姓名",obj.student_set.all().values("name"))

二、需要掌握的一个很重要的知识点

1、form表单中要用submit,如果用button切记要加上type,不然button默认的type是submit,会有影响

  <button class="login" type="button">注册</button>

<button type="button" onclick="doValidation();">提交</button>
<input type="button" onclick="doValidation();" value="提交"/>
上面两种写法是对的,功能一样。

<button onclick="doValidation();">提交</button>
如果写成这种,默认为submit,本来doValidation方法里有提交功能了,
再加上按钮也是提交功能,会提交两次。所以使用按钮时最好指定type类型。
 
  • 相关阅读:
    Spring Boot 之Profile
    Spring Security初识
    Github使用进阶
    数据库JDBC
    Java内存模型(JMM)的可见性
    Spring Boot 整合Spring Data JPA
    Git版本控制工具初识
    Linux美化——终端提示符
    Python's Exception 层级结构
    试写Python内建函数range()
  • 原文地址:https://www.cnblogs.com/xiaohema/p/8456307.html
  • 一、多对多的正反向查询

    class Class(models.Model):
        name = models.CharField(max_length=32,verbose_name="班级名")
        course = models.CharField(verbose_name="课程",max_length=32)
        def __str__(self):
            return self.name
    
    class Teacher(models.Model):
        name = models.CharField(max_length=23,verbose_name="姓名")
        classes = models.ManyToManyField(verbose_name="所属班级",to="Class")
        def __str__(self):
            return self.name

    题目1:查找娜娜老师所带的班级

            # 方式一:基于对象的查找
            obj = models.Teacher.objects.filter(name="娜娜").first()
            print(obj.classes.all())
            print("娜娜老师带的班级",obj.classes.values("name"))
            # 方式二:基于双下划线的查找
            obj_cls = models.Teacher.objects.filter(name="娜娜").values("classes__name")
            print("娜娜老师带的班级",obj_cls)

    注意:要说明的是多对多的查询用.all,,查单个的时候用.values或者values_list,不要用obj.classes.name,,这样查到的会是None,反向查询也是如此。我就是犯了这样的错,引以为戒。。

    总结:不管是一对多,还是多对多,要是查询多得一方就得用all()

    运行结果截图:

    Django 【补充】ORM多对多正向查询

    表结构:

    from django.db import models
    
    # Create your models here.
    # 一个学生有一个班级,一个班级可以有好多学生,所以是
    # 一对多的关系,关联字段放在多的一方
    class Student(models.Model):
        name = models.CharField(max_length=32,verbose_name="姓名")
        age = models.IntegerField(verbose_name="年龄")
        classes = models.ForeignKey(to="Class",verbose_name="所属班级")
        def __str__(self):
            return self.name
    
    class Class(models.Model):
        name = models.CharField(max_length=32,verbose_name="班级名")
        course = models.CharField(verbose_name="课程",max_length=32)
        def __str__(self):
            return self.name
    
    class Teacher(models.Model):
        name = models.CharField(max_length=23,verbose_name="姓名")
        classes = models.ManyToManyField(verbose_name="所属班级",to="Class")
        def __str__(self):
            return self.name

    2、查询海燕在那个班级

      # 方式一:
        print("海燕所在的班级",models.Student.objects.filter(name="海燕").values("classes__name"))
        # 方式二:
        obj_cls = models.Student.objects.filter(name="海燕").first()
        print("海燕所在的班级",obj_cls.classes.name)

    3、查询海燕所在班的老师的姓名

      print("海燕所在班的老师的姓名",models.Student.objects.filter(name="海燕").values("classes__teacher__name"))

    4、查询软件测试151班的所有学生的姓名

     print("软件测试151班的所有学生的姓名",models.Class.objects.filter(name="软件测试151").values("student__name"))
     obj = models.Class.objects.filter(name="软件测试151").first()
     # print("软件测试151班的所有学生的姓名",obj.student_set.name)  #这样打印的结果是None
     print("软件测试151班的所有学生的姓名",obj.student_set.all().values("name"))

    二、需要掌握的一个很重要的知识点

    1、form表单中要用submit,如果用button切记要加上type,不然button默认的type是submit,会有影响

      <button class="login" type="button">注册</button>

    <button type="button" onclick="doValidation();">提交</button>
    <input type="button" onclick="doValidation();" value="提交"/>
    上面两种写法是对的,功能一样。
    
    <button onclick="doValidation();">提交</button>
    如果写成这种,默认为submit,本来doValidation方法里有提交功能了,
    再加上按钮也是提交功能,会提交两次。所以使用按钮时最好指定type类型。