1. 創建數據表並添加數據
創建用戶表和用戶類型表,用戶類型表是用戶表的父表,用戶表是用戶類型的字表。
models.py:
class UserType(models.Model):
"""
用戶類型表
"""
title = models.CharField(max_length=32)
class UserInfo(models.Model):
"""
用戶表
"""
name = models.CharField(max_length=16)
age = models.IntegerField()
ut = models.ForeignKey('UserType', on_delete=models.CASCADE)
views.py:
:
def user(request):
models.UserType.objects.create(title='普通用戶')
models.UserType.objects.create(title='VIP用戶')
models.UserInfo.objects.create(name='Thanlon', age=20, ut_id=1)
models.UserInfo.objects.create(name='Kiku', age=23, ut_id=2)
return HttpResponse('...')
2. 正向連表操作
正向連表查的是UserInfo表,是通過UserInfo表的外健ut字段來獲取父表與之對應的字段。一個用戶只有一個用戶類型
。
def user(request):
result = models.UserInfo.objects.all()
for obj in result:
# print(obj.id,obj.name,obj.age,obj.ut,obj.ut.id,obj.ut.title)
# 如果UserType還有父表則繼續使用.的方式獲取父表的值(三個表,四個表...都可以通過這種方式)
print(obj.id, obj.name, obj.age, obj.ut.title)
"""
2 Thanlon 20 普通用戶
3 Kiku 23 VIP用戶
"""
return HttpResponse('...')
3. 反向連表操作
反向連表查詢的父表UserType,通過父表隱藏的字段來獲取子表UserInfo的字段,這個“隱藏”的字段的格式是 表名_set
。一個用戶類型下可以有多個用戶
。
def user(request):
# 一個用戶類型下可以有多個用戶
# obj = models.UserType.objects.first()
# print(obj.id, obj.title, obj.userinfo_set.all())
"""
1 普通用戶 <QuerySet [<UserInfo: UserInfo object (2)>]>
"""
# 查所有用戶類型下所有的用戶
result = models.UserType.objects.all()
for obj in result:
for row in obj.userinfo_set.all():
print(row.id, row.name, row.age, row.ut.title)
"""
2 Thanlon 20 普通用戶
3 Kiku 23 VIP用戶
"""
return HttpResponse('...')
如果是查Userinfo的所有字段,使用反向連表和正向連表都能查詢到結果,但是我們發現反向連表的時間複雜度比正向連表要大。
反向連表可以獲取用戶類型下對應的所有用戶,還可以通過過濾這些用戶:
def user(request):
obj = models.UserType.objects.first()
print(obj.id, obj.title, obj.userinfo_set.filter(name='Thanlon'))
for row in obj.userinfo_set.filter(name='Thanlon'):
print(row.id, row.name, row.ut.title)
"""
1 普通用戶 <QuerySet [<UserInfo: UserInfo object (2)>]>
2 Thanlon 普通用戶
"""
return HttpResponse('...')
4. 獲取數據的三種方式
第一種方式,獲取的是對象:
def user(request):
result = models.UserType.objects.all()
print(result) # [obj,obj,obj,,,]
"""
<QuerySet [<UserInfo: UserInfo object (2)>, <UserInfo: UserInfo object (3)>]>
"""
for obj in result:
for row in obj.userinfo_set.all():
print(row.id, row.name, row.ut.title)
"""
2 Thanlon 普通用戶
3 Kiku VIP用戶
"""
return HttpResponse('...')
第二種方式,獲取的是字典:
def user(request):
# 獲取所有字段
# result = models.UserInfo.objects.values()
# 獲取指定字段
result = models.UserInfo.objects.values('age', 'name', 'ut__title')
print(
result) # [{'age': 20, 'name': 'Thanlon', 'ut__title': '普通用戶'}, {'age': 23, 'name': 'Kiku', 'ut__title': 'VIP用戶'}]
"""
<QuerySet [{'age': 20, 'name': 'Thanlon', 'ut__title': '普通用戶'}, {'age': 23, 'name': 'Kiku', 'ut__title': 'VIP用戶'}]>
"""
for row in result:
print(row['age'], row['name'], row['ut__title'])
"""
20 Thanlon 普通用戶
23 Kiku VIP用戶
"""
return HttpResponse('...')
第三種方式,獲取的是元組:
def user(request):
# 獲取所有字段
# result = models.UserInfo.objects.values_list()
# 獲取指定字段
result = models.UserInfo.objects.values_list('age', 'name', 'ut__title')
print(result) # [(20, 'Thanlon', '普通用戶'), (23, 'Kiku', 'VIP用戶')]
"""
<QuerySet [(20, 'Thanlon', '普通用戶'), (23, 'Kiku', 'VIP用戶')]>
"""
for row in result:
print(row[0], row[1], row[2])
"""
20 Thanlon 普通用戶
23 Kiku VIP用戶
"""
return HttpResponse('...')
三種方式都支持跨表操作,只不過對象的方式跨表是在循環對象的時候,而字典和元組的方式是在查詢的的時候。