django初窥性能优化

理解我们为什么优化?优化的瓶颈在哪,在条件清楚后我们才好对症下药。

 一:性能度量分析

django-silk地址:
GitHub - jazzband/django-silk: Silky smooth profiling for Django

https://docs.djangoproject.com/zh-hans/2.1/topics/performance/

二:优化方式

1.缓存机制(可以将下静态数据或更新频率较小的做缓存)

内存缓存:memcached
数据库缓存: redis(django-redis)
文件系统缓存:file

2.ORM

1. persistment database connections(持久化连接)
2.Django中的惰性会延迟计算,只有真正需要的时候才会去计算,避免过早地对 QuerySet 进行计算,可以节省对数据库进行一次昂贵而不必要的访问
3. queryset会在缓存,尽量重用
4. use the with template tag,use iterator(),use explain()
5. Do database work in the database rather than in python 
   用blogs.objects.exclude blog.objects.filter查询过滤
   queryset.count 代替len(queryset)
   queryset.exists 代替if queryset
5. 只取需要的数据
   blog.objects.values()    返回字典列表
   blog.objects.values_list() 返回元组列表
   blog.objects.defer('name') 排除不需要的字段
   blog.objects.only('name') 仅取需要的字段
6. 关联查询blog.objects.select_related.get() 尽量深入查询关联的数据(大量外键时
   entry.blog_name代替entry.blog.name 
   select_related: 仅限于单值关系 - 外键(多对一)和一对一
   prefetch_related: 预取 多对多和多对一对象

8.使用queryset.update和queryset.delete来批量处理

select_related:对于一对一字段(OneToOneField)和多对一字段(ForeignKey),可以使用select_related 来对QuerySet进行优化。select_related使获取相应外键对应的对象,不必再查询数据库了。原理:select_related使用SQL的JOIN语句进行优化,通过减少SQL查询的次数来进行优化、提高性能。

# 深度
queryset = Person.objects.select_related(depth=3)
# 外键的外键的字段名
queryset = Person.objects.select_related("hometown__province","living__province").all()
# 链式
queryset = Person.objects.select_related("hometown__province").select_relate("living_province").all()
for item in queryset:
    print(item.hometown.province)
    print(item.living.province) 


prefetch_related: 2.对于多对多字段(ManyToManyField)和一对多字段,可以使用prefetch_related()来进行优化。原理:不用sql语句解决,分别查询每个表,用python处理之间的关系。注意:可以在调用prefetch_related之前调用select_related。先select_related,然后利用缓存到的数据prefetch_related。然而prefetch_related已经调用,select_related将不起作用。

queryset = Person.objects.prefetch_related("visitation__province").all()

for item in queryset:
    for city in item.visitation.all():
         print(city.province)

# QuerySet链式操作改变了数据库请求,之前用的prefetch_related缓存将被忽略,会重新请求数据库.
# 如:
    for city in item.visitation.filter(name__icontains=""):
         print(city.province)

3.数据库读写分离

采用数据读写分离,降低数据库压力

4.celery

对不需要立即返回的,可以借助于celery做异步任务

5.部署方案

使用高性能的部署策略

 nginx+uWSGI+django
 nginx+gunicorn+django 
 nginx+apache+mod_wsgi+django

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值