Django代码性能优化与Pycharm Profile使用详解


Posted in Python onAugust 26, 2018

前言

pycharm是python的一个商业的集成开发工具,本人感觉做python开发还是很好用的,django是一个很流行的python web开源框架,本文将通过实例代码给大家介绍了关于Django代码性能优化与Pycharm Profile使用的相关内容,分享出来供大家参考学习,下面话不多说了,来一起看看详细的介绍吧

是一段导出数据月报的脚本,原先需要十几秒,优化后只需要1秒多。

Pycharm Profile

优化第一步就是Profile,先看看慢在哪里。Pycharm自带Profile工具,很方便。
拿一张官方图说明一下。

Django代码性能优化与Pycharm Profile使用详解

图表说明:

  • 给出了函数调用关系。
  • 红色->黄绿色->绿色,颜色越深说明耗时越多。
  • 右上角的“x数字”代表函数调用次数。
  • Own代表该函数本身的耗时,不包括调用子函数;而Total包括调用子函数的耗时。还给出了耗时的百分比。
  • 可以右键“jump to source”,跳到对应的源码。

有了Profile,剩下的事情就好办了。

首先,看到了有个工具函数调用了9千多次,这个函数用到了nametupled,花了很多时间,于是把nametupled去掉,节省了好几秒的时间。

开启Django logger并设置DEBUG级别

继续Profile,看到时间主要在ORM查询数据库那里。
这时,开启Django本身的logger,级别调到DEBUG,这样就会打印出查询的SQL语句。

N+1问题

首先意识到的是ORM查询的N+1问题。

比如有个Order表,里面有个外键user_id是关联User表.当我们

for order in Order.objects.all():
 order.user.id

的时候,Order.objects.all()只有1条sql语句,获取Order表本身的字段到内存,而不会将关联的外键也获取。

当我们order.user_id的时候,不会触发额外的sql查询,而order.user.id的时候,会额外查询User表。

for循环执行了N次,就额外sql查询了N次。故叫N+1问题。

解决N+1的方法:

  • 如果是只用到id字段,则可以直接用user_id代替user.id
  • select_related。将相关的表也一同查询。select_related如果不传参数,表示查询所有外键的表。

又节省了几秒的时间。

只查询需要的字段

继续看log,发现sql查询次数是减少了很多,然而sql查询语句很长,看来是把所有字段都查询出来。

然而我很多时候只需要某几个字段而已,这样全查出来就浪费了。

解决方法:

  • only()。只查询想要的字段。比如Order.objects.only(‘user_id', ‘pay_date', ‘price')
  • annotate()。 可指定虚拟字段,如果外键关联的表只用到小部分字段,可以直接annotate过来。比如将User表的realname字段赋给Order表叫user_realname虚拟字段.这样就不需要order.user.realname查询,只需要order.user_realname来查询,不用select_related把user表全部字段给取出来。Order.objects.annotate(user_realname=F(‘user__realname'))。注意还用到了F(),表示纯数据库层面的操作,不需要拉到python内存进行处理。

An F() object represents the value of a model field or annotated column. It makes it possible to refer to model field values and perform database operations using them without actually having to pull them out of the database into Python memory.

至此,将整段代码的执行时间减少到了1.5秒。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持。

Python 相关文章推荐
在Python程序中实现分布式进程的教程
Apr 28 Python
python使用matplotlib绘制折线图教程
Feb 08 Python
Python pygorithm模块用法示例【常见算法测试】
Aug 16 Python
Python中正则表达式的用法总结
Feb 22 Python
python+os根据文件名自动生成文本
Mar 21 Python
selenium跳过webdriver检测并模拟登录淘宝
Jun 12 Python
Python 实现数组相减示例
Dec 27 Python
python 在右键菜单中加入复制目标文件的有效存放路径(单斜杠或者双反斜杠)
Apr 08 Python
Python打印特殊符号及对应编码解析
May 07 Python
python从Oracle读取数据生成图表
Oct 14 Python
Python爬虫获取op.gg英雄联盟英雄对位胜率的源码
Jan 29 Python
浅谈Python响应式类库RxPy
Jun 14 Python
django利用request id便于定位及给日志加上request_id
Aug 26 #Python
python如何创建TCP服务端和客户端
Aug 26 #Python
Django压缩静态文件的实现方法详析
Aug 26 #Python
Python实现将Excel转换成xml的方法示例
Aug 25 #Python
Python实现的简单计算器功能详解
Aug 25 #Python
Python基于OpenCV库Adaboost实现人脸识别功能详解
Aug 25 #Python
Python使用matplotlib绘制三维图形示例
Aug 25 #Python
You might like
雄兵连:天使彦天使彦为爱折翼,彦和炙心同时念动的誓言!
2020/03/02 国漫
PHP实现原比例生成缩略图的方法
2016/02/03 PHP
PHP调用API接口实现天气查询功能的示例
2017/09/21 PHP
JavaScript 设计模式之组合模式解析
2010/04/09 Javascript
js添加table的行和列 具体实现方法
2013/07/22 Javascript
js获取当前月的第一天和最后一天的小例子
2013/11/18 Javascript
引用其它js时如何同时处理多个window.onload事件
2014/09/02 Javascript
详解JavaScript基于面向对象之创建对象(1)
2015/12/10 Javascript
浅析BootStrap Treeview的简单使用
2016/10/12 Javascript
Vue按需加载的具体实现
2017/12/02 Javascript
详解node Async/Await 更好的异步编程解决方案
2018/05/10 Javascript
jQuery实现导航样式布局操作示例【可自定义样式布局】
2018/07/24 jQuery
VUE-Table上绑定Input通过render实现双向绑定数据的示例
2018/08/27 Javascript
vue中使用heatmapjs的示例代码(结合百度地图)
2018/09/05 Javascript
在Layui中实现开关按钮的效果实例
2019/09/29 Javascript
[50:58]2018DOTA2亚洲邀请赛3月29日 小组赛A组OpTic VS Newbee
2018/03/30 DOTA
使用Python操作Elasticsearch数据索引的教程
2015/04/08 Python
在Python的Flask框架下收发电子邮件的教程
2015/04/21 Python
Python中内置数据类型list,tuple,dict,set的区别和用法
2015/12/14 Python
运动检测ViBe算法python实现代码
2018/01/09 Python
Python多线程threading和multiprocessing模块实例解析
2018/01/29 Python
django框架两个使用模板实例
2019/12/11 Python
使用Python实现批量ping操作方法
2020/05/06 Python
详解python tkinter包获取本地绝对路径(以获取图片并展示)
2020/09/04 Python
HTML5所有标签汇总及标签意义解释
2015/03/12 HTML / CSS
详解HTML5中div和section以及article的区别
2015/07/14 HTML / CSS
世界上最大的二手相机店:KEN
2017/05/17 全球购物
经典c++面试题四
2015/05/14 面试题
技术总监岗位职责
2013/12/05 职场文书
大学生旷课检讨书
2014/01/22 职场文书
大学教师师德师风演讲稿
2014/08/22 职场文书
2014年教师节演讲稿
2014/09/03 职场文书
2015年党风廉政建设责任书
2015/01/29 职场文书
MySQL和Oracle批量插入SQL的通用写法示例
2021/11/17 MySQL
Python使用Opencv打开笔记本电脑摄像头报错解问题及解决
2022/06/21 Python
Windows server 2016服务器基本设置
2022/08/14 Servers