zoukankan      html  css  js  c++  java
  • 73.Python中ORM聚合函数详解:Count

    Count:用来求某个数据的个数。

    在以下所有的示例中所采用的模型为:

    from django.db import models
    
    
    # 定义作者模型
    class Author(models.Model):
        name = models.CharField(max_length=100, unique=True)
        age = models.IntegerField()
        email = models.EmailField()
    
        class Meta:
            db_table = 'author'
    
        def __str__(self):
            return "%s,%s,%s" % (self.name,self.age, self.email)
    
    
    # 定义出版社模型
    class Publisher(models.Model):
        name = models.CharField(max_length=100,unique=True)
    
        class Meta:
            db_table = 'publisher'
    
    
    # 定义图书模型
    class Book(models.Model):
        name = models.CharField(max_length=100, unique=True)
        pages = models.IntegerField()
        price = models.FloatField()
        rating = models.FloatField()
        author = models.ForeignKey('Author', on_delete=models.CASCADE)
        publisher = models.ForeignKey('Publisher', on_delete=models.CASCADE)
    
        class Meta:
            db_table = 'book'
    
    
    # 定义预定图书的模型
    class BookOrder(models.Model):
        book = models.ForeignKey('Book', on_delete=models.CASCADE)
        price = models.FloatField()
    
        class Meta:
            db_table = 'book_order'
    

    1. 比如:求所有图书的数量,那么views.py视图文件中可以使用以下代码:

    from django.http import HttpResponse
    from .models import Author,Publisher,Book,BookOrder
    from django.db.models import Avg,Count,Sum
    from django.db import connection
    
    
    def index(request):
    # 4.求所有图书的数量,因为book表中的数据具有唯一性所以可以通过计算ID的唯一性来计算图书的数量。
        count = Book.objects.aggregate(book_count=Count('id'))
        print(count)
        # 打印出结果为:{'book_count': 4}
        return HttpResponse("success !")
    
    

    2.求同一种书预定的数量

    from django.http import HttpResponse
    from .models import Author,Publisher,Book,BookOrder
    from django.db.models import Avg,Count,Sum
    from django.db import connection
    
    
    def index(request):
    # 5.求同一种书的预定数量,同样还是针对book表,此处可以是针对bookorder__id,也可以是bookorder。默认就是针对book__order表中id字段进行操作
        books = Book.objects.annotate(books_count=Count('bookorder'))
        # print(type(books))
        # <class 'django.db.models.query.QuerySet'>
        # 遍历QuerySet
        for book in books:
            print("%s,%s" % (book.name,book.books_count))
        # 打印出结果:
        # 三国演义,2
        # 水浒传,2
        # 红楼梦,2
        # 西游记,0
    # 打印出原生SQL语句
        print(connection.queries)
    # 打印出结果:[{'sql': 'SELECT @@SQL_AUTO_IS_NULL', 'time': '0.000'}, {'sql': 'SET SESSION TRANSACTION ISOLATION LEVEL READ COMMITTED', 'time': '0.000'}, {'sql': 'SELECT `book`.`id`, `book`.`name`, `book`.`pages`, `book`.`price`, `book`.`rating`, `book`.`author_id`, `book`.`publisher_id`, COUNT(`book_order`.`id`) AS `books_count` FROM `book` LEFT OUTER JOIN `book_order` ON (`book`.`id` = `book_order`.`book_id`) GROUP BY `book`.`id` ORDER BY NULL', 'time': '0.000'}]
        return HttpResponse("success !")
    
    

    3. 同样Count()可以传递参数distinct,默认情况下,distinct=False.可以通过指定distinct=True,删除返回值中相同的数据。例如:求被预定的书有多少种书,示例代码如下:

    from django.http import HttpResponse
    from .models import Book
    from django.db.models import Count
    
    
    def index(request):
    # 6.求被预定的书都有多少种书
    # 首先可以使用annotate()进行分组,之后对分组的数据进行删除相同的数据操作。
        book_nums = Book.objects.annotate(book_nums=Count('bookorder', distinct=True))
        print(book_nums)
        return HttpResponse("success !")
    
    打印出结果:

    打印出的结果为QuerySet对象,不容易分辨具体的数据信息。因此我们可以对Book模型的__str__(self)方法进行重写。

    <QuerySet [<Book: Book object (1)>, 
    <Book: Book object (2)>, 
    <Book: Book object (3)>, 
    <Book: Book object (4)>]>
    
    

    重写模型的__str__(self)方法:

    # 定义出版社模型
    class Publisher(models.Model):
        name = models.CharField(max_length=100,unique=True)
    
        class Meta:
            db_table = 'publisher'
    
        def __str__(self):
            return " ->:%s" % self.name
    
    
    # 定义图书模型
    class Book(models.Model):
        name = models.CharField(max_length=100, unique=True)
        pages = models.IntegerField()
        price = models.FloatField()
        rating = models.FloatField()
        author = models.ForeignKey('Author', on_delete=models.CASCADE)
        publisher = models.ForeignKey('Publisher', on_delete=models.CASCADE)
    
        class Meta:
            db_table = 'book'
    
        def __str__(self):
            return "(书名:%s,页数:%s,价格:%s,打折:%s,作者:%s,出版社:%s)" % (self.name, self.pages, self.price, self.rating, self.author, self.publisher)
    
    
    打印出结果:
    <QuerySet [
    <Book: (书名:三国演义,页数:893,价格:129.0,打折:0.8,作者:罗贯中,47,312587329@qq.com,出版社: ->:清华大学出版社)>, 
    <Book: (书名:水浒传,页数:983,价格:159.0,打折:0.75,作者:施耐庵,57,1924572@qq.com,出版社: ->:吉林大学出版社)>, 
    <Book: (书名:红楼梦,页数:1543,价格:199.0,打折:0.85,作者:曹雪芹,42,123521472@qq.com,出版社: ->:浙江大学出版社)>, 
    <Book: (书名:西游记,页数:1003,价格:159.0,打折:0.75,作者:吴承恩,34,193452272@qq.com,出版社: ->:清华大学出版社)>
    ]>
    
    
    始于才华,忠于颜值;每件事情在成功之前,看起来都是天方夜谭。一无所有,就是无所不能。
  • 相关阅读:
    codevs 1115 开心的金明
    POJ 1125 Stockbroker Grapevine
    POJ 2421 constructing roads
    codevs 1390 回文平方数 USACO
    codevs 1131 统计单词数 2011年NOIP全国联赛普及组
    codevs 1313 质因数分解
    洛谷 绕钉子的长绳子
    洛谷 P1276 校门外的树(增强版)
    codevs 2627 村村通
    codevs 1191 数轴染色
  • 原文地址:https://www.cnblogs.com/guyan-2020/p/12257662.html
Copyright © 2011-2022 走看看