Python3如何使用多线程升程序运行速度


Posted in Python onAugust 11, 2020

优化前后新老代码如下:

from git_tools.git_tool import get_collect_projects, QQNews_Git
from threading import Thread, Lock
import datetime

base_url = "http://git.xx.com"
project_members_commits_lang_info = {}
lock = Lock()
threads = []

'''
Author:zenkilan
'''


def count_time(func):
  def took_up_time(*args, **kwargs):
    start_time = datetime.datetime.now()
    ret = func(*args, **kwargs)
    end_time = datetime.datetime.now()
    took_up_time = (end_time - start_time).total_seconds()
    print(f"{func.__name__} execution took up time:{took_up_time}")
    return ret

  return took_up_time


def get_project_member_lang_code_lines(git, member, begin_date, end_date):
  global project_members_commits_lang_info
  global lock
  member_name = member["username"]
  r = git.get_user_info(member_name)
  if not r["id"]:
    return
  user_commits_lang_info = git.get_commits_user_lang_diff_between(r["id"], begin_date, end_date)
  if len(user_commits_lang_info) == 0:
    return
  lock.acquire()
  project_members_commits_lang_info.setdefault(git.project, dict())
  project_members_commits_lang_info[git.project][member_name] = user_commits_lang_info
  lock.release()


def get_project_lang_code_lines(project, begin_date, end_date):
  global threads
  git = QQNews_Git(project[1], base_url, project[0])
  project_members = git.get_project_members()
  if len(project_members) == 0:
    return
  for member in project_members:
    thread = Thread(target=get_project_member_lang_code_lines, args=(git, member, begin_date, end_date))
    threads.append(thread)
    thread.start()


@count_time
def get_projects_lang_code_lines(begin_date, end_date):
  """
  获取项目代码行语言相关统计——新方法(提升效率)
  应用多线程替代for循环
  并发访问共享外部资源
  :return:
  """
  global project_members_commits_lang_info
  global threads
  for project in get_collect_projects():
    thread = Thread(target=get_project_lang_code_lines, args=(project, begin_date, end_date))
    threads.append(thread)
    thread.start()


@count_time
def get_projects_lang_code_lines_old(begin_date, end_date):
  """
  获取项目代码行语言相关统计——老方法(耗时严重)
  使用最基本的思路进行编程
  双层for循环嵌套并且每层都包含耗时操作
  :return:
  """
  project_members_commits_lang_info = {}
  for project in get_collect_projects():
    git = QQNews_Git(project[1], base_url, project[0])
    project_members = git.get_project_members()
    user_commits_lang_info_dict = {}
    if len(project_members) == 0:
      continue
    for member in project_members:
      member_name = member["username"]
      r = git.get_user_info(member_name, debug=False)
      if not r["id"]:
        continue
      try:
        user_commits_lang_info = git.get_commits_user_lang_diff_between(r["id"], begin_date, end_date)
        if len(user_commits_lang_info) == 0:
          continue
        user_commits_lang_info_dict[member_name] = user_commits_lang_info
        project_members_commits_lang_info[git.project] = user_commits_lang_info_dict
      except:
        pass
  return project_members_commits_lang_info


def test_results_equal(resultA, resultB):
  """
  测试方法
  :param resultA:
  :param resultB:
  :return:
  """
  print(resultA)
  print(resultB)
  assert len(str(resultA)) == len(str(resultB))


if __name__ == '__main__':
  from git_tools.config import begin_date, end_date

  get_projects_lang_code_lines(begin_date, end_date)
  for t in threads:
    t.join()
  old_result = get_projects_lang_code_lines_old(begin_date, end_date)
  test_results_equal(old_result, project_members_commits_lang_info)

老方法里外层for循环和内层for循环里均存在耗时操作:

1)git.get_project_members()

2)git.get_user_info(member_name, debug=False)

分两步来优化,先里后外或先外后里都行。用多线程替换for循环,并发共享外部资源,加锁避免写冲突。

测试结果通过,函数运行时间装饰器显示(单位秒):

get_projects_lang_code_lines execution took up time:1.85294

get_projects_lang_code_lines_old execution took up time:108.604177

速度提升了约58倍

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python之Socket网络编程详解
Sep 29 Python
python妙用之编码的转换详解
Apr 21 Python
Python3 log10()函数简单用法
Feb 19 Python
python可视化爬虫界面之天气查询
Jul 03 Python
Apache部署Django项目图文详解
Jul 30 Python
详解python中的index函数用法
Aug 06 Python
Ubuntu16.04安装python3.6.5步骤详解
Jan 10 Python
Python3标准库glob文件名模式匹配的问题
Mar 13 Python
用python给csv里的数据排序的具体代码
Jul 17 Python
Python和Bash结合在一起的方法
Nov 13 Python
Python 如何将integer转化为罗马数(3999以内)
Jun 05 Python
Elasticsearch 数据类型及管理
Apr 19 Python
使用Python pip怎么升级pip
Aug 11 #Python
python中通过pip安装库文件时出现“EnvironmentError: [WinError 5] 拒绝访问”的问题及解决方案
Aug 11 #Python
Python 代码调试技巧示例代码
Aug 11 #Python
python+pygame实现坦克大战小游戏的示例代码(可以自定义子弹速度)
Aug 11 #Python
Python函数递归调用实现原理实例解析
Aug 11 #Python
零基础学python应该从哪里入手
Aug 11 #Python
Python如何测试stdout输出
Aug 10 #Python
You might like
收集的PHP中与数组相关的函数
2007/03/22 PHP
PHP令牌 Token改进版
2008/07/18 PHP
检测png图片是否完整的php代码
2010/09/06 PHP
IIS6.0 开启Gzip方法及PHP Gzip函数分享
2014/06/08 PHP
Tips 带三角可关闭的文字提示
2010/10/06 Javascript
15个款优秀的 jQuery 图片特效插件推荐
2011/11/21 Javascript
javascript定义变量时带var与不带var的区别分析
2015/01/12 Javascript
JavaScript控制table某列不显示的方法
2015/03/16 Javascript
jQuery实现监控页面所有ajax请求的方法
2015/12/10 Javascript
ExtJS 4.2 Grid组件单元格合并的方法
2016/10/12 Javascript
原生js实现类似fullpage的单页/全屏滚动
2017/01/22 Javascript
vue双向绑定简要分析
2017/03/23 Javascript
Bootstrap实现的标签页内容切换显示效果示例
2017/05/25 Javascript
详解Vue学习笔记入门篇之组件的内容分发(slot)
2017/07/17 Javascript
利用Decorator如何控制Koa路由详解
2018/06/26 Javascript
vue左侧菜单,树形图递归实现代码
2018/08/24 Javascript
[01:13:18]Secret vs Infamous 2019国际邀请赛淘汰赛 败者组 BO3 第一场 8.23
2019/09/05 DOTA
DataFrame 将某列数据转为数组的方法
2018/04/13 Python
python 文本单词提取和词频统计的实例
2018/12/22 Python
Python面向对象之类和实例用法分析
2019/06/08 Python
python里 super类的工作原理详解
2019/06/19 Python
python用win32gui遍历窗口并设置窗口位置的方法
2019/07/26 Python
Django上线部署之IIS的配置方法
2019/08/22 Python
Python 内置变量和函数的查看及说明介绍
2019/12/25 Python
浅谈python累加求和+奇偶数求和_break_continue
2020/02/25 Python
浅谈如何使用python抓取网页中的动态数据实现
2020/08/17 Python
详解css3 mask遮罩实现一些特效
2018/10/24 HTML / CSS
定义css设备类型-Media Queries图表简介及使用方法
2013/01/21 HTML / CSS
HTML5微信播放全屏问题的解决方法
2017/03/09 HTML / CSS
俄罗斯旅游网站:Tripadvisor俄罗斯
2017/03/21 全球购物
Anya Hindmarch官网:奢侈设计师手袋及配饰
2018/11/15 全球购物
Nasty Gal英国:美国女性服饰销售网站
2021/03/02 全球购物
什么是网络协议
2016/04/07 面试题
开工庆典邀请函范文
2014/01/16 职场文书
学校教研活动总结
2014/07/02 职场文书
会计专业自荐书
2014/07/08 职场文书