1. 程式人生 > >python自動化學習筆記之DAY19

python自動化學習筆記之DAY19

primary queryset imp 正向查詢 tom 使用 mov orm 復雜

Django-model基礎

表的創建(模型建立)

例1:
from django.db import models
#書籍
class Book(models.Model):
    id=models.AutoField(primary_key=True)
    title=models.CharField(max_length=32)
    pubDate=models.DateField()
    price=models.DecimalField(max_digits=6,decimal_places=2)

    # 書籍與出版社: 一對多
    publisher=models.ForeignKey(to="
Publish",related_name="bookList") # 書籍與作者: 多對多 authors=models.ManyToManyField("Author") #出版社 class Publish(models.Model): name=models.CharField(max_length=32) addr=models.CharField(max_length=32) tel=models.BigIntegerField() #作者 class Author(models.Model): name=models.CharField(max_length=32) age
=models.IntegerField() tel=models.CharField(max_length=32) #作者詳細信息 class AuthorDetail(models.Model): addr=models.CharField(max_length=32) #作者與作者詳細信息:一對一的 author=models.OneToOneField("Author")

說明:

(1)、id字段是自動添加的

(2)、對於外鍵字段,Django會在字段名上添加“_id”來創建數據庫中的列名

(3)、外鍵字段ForeignKey有一個null=True的設置,他可以為空置NULL,可以賦值None

1、 查詢表記錄

all():查詢所有結果,例如:查詢所有書籍信息:models.Book.objects.all()

filter(**kwargs):過濾的出的是對象集合(QuerySet) 例如:過濾名稱為Python的書籍,models.Book.objects.filter(title=“Python”)

get(**kwargs):返回結果為對象,有且只有一個,如果有多個會報錯

values(**kwargs):返回一個ValueQuerySet,一個特殊的QuerySet,運行後得到的是一個可叠代的字典序列,而不是model的實例化對象

value_list(**field):與values()類似,它返回的是一個元祖序列,values返回的是一個字典序列

exclude(**kwargs):返回給篩選條件不匹配的對象

distinct():刪除重復記錄

count():返回數據庫中匹配查詢(QuerySet)的對象數量

first()/last():返回第一條/最後一條記錄

exists():返回布爾值,如果QuerySet有數據,返回True,沒有則返回False

order_by(*field)/reverse():對查詢結果排序/反向排序

2、 添加表記錄

普通字段:

方式1:

models.Book.objects.create(title="python",price=122,pubDate="2012-12-12")

方式2:

obj=models.Book(title="python",price=122,pubDate="2012-12-12")

obj.save()

外鍵字段:

方式1:

publish_obj=models.Publish.objects.get(name="renmin")

book_obj=models.Book.objects.create(title="python",price=122,pubDate="2012-12-12",publisher=publish_obj)

方式2:

book_obj=models.Book.objects.create(title=titles,price=price,pubDate=pubdate,publisher_id=publish_id)

多對多字段

book_obj=models.Book.objects.create(title=title,pubDate=pubdate,price=price,publisher_id=publish_id)

綁定關系

print(book_obj.authors.all()) # <QuerySet []>

book_obj.authors.add(obj,obj2,...)

book_obj.authors.add(*[])

解除關系

book_obj.authors.remove(obj,obj2,...)

book_obj.authors.remove(*[])

清空

book_obj.authors.clear()

3、 class RelatedManager

add([obj1,obj2,…]):把指定的模型對象添加到關聯對象集中。

create(**kwargs):創建一個新的對象,保存對象,並將它添加到關聯對象集之中,返回新創建的對象

remove([obj1,obj2,…]):從關聯對象集中移除執行的模型對象

clear():從關聯對象集中移除一切對象

set():先清空,在設置,編輯替換可以用到

4、 ORM跨表查詢

(1)、基於對象的跨表查詢

#############################一對多查詢###########################

正向查詢:按字段

例如:查詢python這本書的出版社的名稱和地址

book_python=models.Book.objects.filter(title="python").first()

book_python.publisher # Publish object : 與這本書關聯的

book_python.publisher.name 出版社的名稱

book_python.publisher.addr 出版社的地址

反向查詢:按關聯的表名(小寫)_set

例如:查詢人民出版社出版過的所有書籍名稱及價格

pub_obj=models.Publish.objects.get(name="renmin")

book_list=pub_obj.book_set.all() # QuerySet 與這個出版社關聯的所有書籍對象

for obj in book_list:

print(obj.title,obj.price)

#############################一對一查詢###########################

正向查詢:按字段

例如:查詢addr在沙河的作者

authorDetail=models.AuthorDetail.objects.get(addr="shahe")

print(authorDetail.author.name) # alex

反向查詢:按表名(小寫)

查詢 alex混跡在哪裏

alex=models.Author.objects.get(name="alex")

print(alex.authordetail.addr) # shahe

#############################多對多查詢###########################

正向查詢:按字段

例如:查詢 python這本書的所有作者的姓名和年齡

book_python=models.Book.objects.get(title="python")

author_list=book_python.authors.all()

for obj in author_list:

print(obj.name,obj.age)

book_pythons = models.Book.objects.filter(title="python")

for book_python in book_pythons:

author_list = book_python.authors.all()

for obj in author_list:

print(obj.name, obj.age)

反向查詢:按關聯的表名(小寫)_set

例如:alex出版過的所有書籍的明顯名稱

alex=models.Author.objects.get(name="alex")

book_list=alex.book_set.all()

for i in book_list:

print(i.title,i.price)

(2)基於雙下劃線的跨表查詢

正向查詢:按字段

反向查詢:按表名

例1:查詢python這本書的價格

ret=models.Book.objects.filter(title="python").values("price","title")
print(ret) # <QuerySet [{‘price‘: Decimal(‘122.00‘)}]>

例2:查詢python這本書的出版社的名稱和地址

正向查詢 按字段 基於book表
ret2=models.Book.objects.filter(title="python").values_list("publisher__name")

反向查詢 按表名 if 設置了related_name: 按設置值
ret3=models.Publish.objects.filter(bookList__price=333).values_list("name","addr").distinct()

例3:查詢人民出版社出版過的所有書籍名稱及價格

ret4=models.Book.objects.filter(publisher__name="renmin").values("title","price")

ret5=models.Publish.objects.filter(name="renmin").values("bookList__title","bookList__price")

例4:查詢egon出過的所有書籍的名字(多對多)

ret6=models.Author.objects.filter(name="egon").values_list("book__title")

ret7=models.Book.objects.filter(authors__name__contains="eg").values("title")

例5:地址以沙河開頭的的作者出版過的所有書籍名稱以及出版社名稱

ret8=models.Book.objects.filter(authors__authordetail__addr__startswith="sha").values("title","publisher__name")

(3)回顧聚合與分組

①、 聚合函數 SUM AVG MIN MAX COUNT
②、聚合函數可以單獨使用,不一定要和分組配合使用;只不過聚合函數與group by 搭配
③、 統計每一個部門有多少人: select COUNT(name) from emp group by dep_id
select book.id ,book.title,count(1) from book join bookAuthor on book.id=bookAuthor.book_id group by book.id,book.title,

單純聚合函數
計算所有圖書的平均價格
ret=models.Book.objects.all().aggregate(priceSum=Sum("price"))
print(ret) # {‘priceSum‘: Decimal(‘2158.00‘)}

統計每一本書的作者個數

ret2=models.Book.objects.all().annotate(authors_num=Count("authors")) # QuerySet
print(ret2) # [book_obj1,book_obj2,book_obj3,book_obj4,....]

for obj in ret2:
  print(obj.nid,obj.title,obj.authors_num)


查詢每一個出版社出版過的所有書籍的總價格

方式1:
ret3=models.Publish.objects.all().annotate(priceSum=Sum("bookList__price"))

for obj in ret3:
   print(obj.id,obj.name,obj.priceSum)

ret4 = models.Publish.objects.all().annotate(priceSum=Sum("bookList__price")).values("name","priceSum")
print(ret4)

方式2:
ret5=models.Book.objects.all().values("publisher__name").annotate(priceSum=Sum("price")).values("publisher__name","priceSum")
print(ret5)

(4)F與Q查詢

from django.db.models import F,Q

F查詢:F()的實例可以在查詢中引用字段,來比較同一個model實例中兩個不同字段的值

###################################F查詢

ret1=models.Book.objects.filter(comment_num__gt=50)

ret2=models.Book.objects.filter(comment_num__gt=F("read_num")*2)

print(ret2)

models.Book.objects.all().update(price=F("price")+10)

Q查詢:在執行復雜的查詢語句時使用Q對象比較多

Q對象可以組合&、|、~(取反)等操作符以及使用括號進行分組來編寫復雜的對象

################################## Q查詢
ret3=models.Book.objects.filter(comment_num__gt=50,read_num__gt=50)

ret3=models.Book.objects.filter(Q(comment_num__gt=100)|Q(read_num__gt=100))

print(ret3)

註意事項

ret3=models.Book.objects.filter(price__lt=100,(Q(comment_num__gt=100)|Q(read_num__gt=100)))

python自動化學習筆記之DAY19