算法分析(python)
文章目录
- 1.什么是算法分析?
- 2.大O表示法
- 3.变位词的判断问题
- 4. Python数据类型的性能
1.什么是算法分析?
如何对比两个程序?
- 好的程序变量名清晰,无用垃圾代码少。
- 代码风格,可读性
程序和算法的区别
- 算法是对问题解决的分步描述
- 程序则是采用某种编程语言实现的算法
算法分析的概念
- 算法分析主要就是从计算资源消耗的角度来评判和比较算法。更高效利用计算资源,或者更少占用计算资源的算法,就是好算法。
那么何为计算资源?
- 一种是算法解决问题过程中需要的存储空间或内存
- 另一种是算法的执行时间
运行时间检测
- 获取打印111所需时间
import time
start = time.time()
print(111)
end = time.time()
running_time = end-start
print('time cost : %.5f sec' %running_time)
运行结果
111
time cost : 0.00000 sec
- 显示时间是0.00000秒,是因为打印111所需要的时间太短了,所以不是很精确。
如何比较算法的“好坏”?
- 衡量算法可从时间空间两个角度分析
有两个不同的算法,都可以计算前n项数的和。
①迭代算法
import time
def sumOfN2(n) :start = time. time( )theSum = 0for i in range(1,n+1):theSum = theSum + iend = time. time( )return theSum, end-start
print("Sum is %d required %10.7f seconds"% sumOfN2 (10000) )
sum is 50005000 requires 0.0007980 seconds
②无迭代算法
import time
def sumOfN3(n) :start = time. time( )theSum=(n*(n+- 1))/2end =time. time( )return theSum ,end-start
sum is 50005000 requires 0.0000010 seconds
第二种算法所需时间更短
观察一下第一种迭代算法
- 包含了一个循环,可能会执行更多语句 这个循环运行次数跟累加值n有关系,n增加,循环次数也增加,执行时间增加
import time
def sumOfN2(n) :theSum = 0for i in range(1,n+1):#就是这条循环语句!!theSum = theSum + ireturn theSum
2.大O表示法
赋值语句 是作为算法时间的度量指标
- 赋值语句执行少,则程序运行时间短。
如何来看赋值语句执行的次数呢?
- 在这个程序中,我们用T(n)来表示赋值语句的条数
def sumOfN2(n) :theSum = 0 #一条赋值语句,T(n)1=1for i in range(1,n+1):#一条循环语句,循环了n次T(n)2=n theSum = theSum +i#一条赋值语句,T(n)2=n*1return theSum
所以对于"问题规模"n,赋值语句数量
T(n)=T(n)1+T(n)2=n+1
什么是问题规模
- 问题规模就是影响算法执行时间最主要的因素。
- 所以对于上面那个程序,前1000个整数求和,对比前100个整数求和,算是较大的问题规模,所以前n个整数累计求和,n就是问题规模了
算法分析目标?
- 算法分析的目标是找出问题规模会怎样影响算法执行时间
数量级函数
- 数量级函数就是用来描述T(n)中随着n增加增加速度最快的主导部分,称作“大O”表示法,记作O(f(n)),其中f(n)表示T(n)中的主导部分
主导部分怎么确定呢?就是T(n)中增长速度最快的部分
T(n)=n+1,主导部分是n
T(n)=200n3+20n+1000,主导部分是n3
影响算法运行时间的因素不只有问题规模,还有其他。
常见的大O数量级函数
f(n) | 名称 |
---|---|
1 | 常数 |
log(n) | 对数 |
n | 线性 |
n*log(n) | 对数线性 |
n2 | 平方 |
n3 | 立方 |
2n | 指数 |
从代码分析执行时间数量级函数
a=5
b=6
c = 10 #3条赋值语句,所以T(n)1=3
for i in range(n): #循环语句nfor j in range(n): #循环语句n,所以T(n)2=n的平方X=i*iY=j*jZ=i*1 #三条赋值语句,所以T(n)2=3n的平方
for k in range(n):#循环语句n,T(n)3=nW =a*k+45V=b*b #两条赋值语句,所以T(n)3=2n
d=33 #1条赋值语句,所以T(n)4=1
所以,T(n)=T(n)1+T(n)2+T(n)3+T(n)4=3+3n2+2n+1=3n2+2n+4
其它算法复杂度表示法
- 大O表示法
表示了所有上限中最小的那个,上限。 - 大Ω表示法
表示了所有下限中最大的那个下限
f(n) = Ω(g(n))当且仅当g(n) = o(f(n)) - 大θ表示法
如果上下限相同,那么就可以用大θ表示 f(n) =θ(g(n)) 当且仅当f(n) = O(g(n))且f(n) = Ω(g(n))
3.变位词的判断问题
- 所谓“变位词”是指两个词之间存在组成字母的重新排列关系。如:heart和earth,python和typhon
- 可以很好展示同一问题的不同数量级算法
写一个bool函数,以两个词作 为参数,返回这两个词是否变位词
解法1:逐字检查
- 思路:将词1中的字符逐个到词2中检查是否存在,存在的字符“打勾”标记,如果每个字符都能找到,则两个词是变位词 。
- 将词2对应“打勾”的字符设为None。由于字符串是不可变类型,需要先复制到列表中:
def anagramSolution(s1,s2):alist = list(s2) #复制s2到列表stillOK = Truepos1 = 0while pos1<len(s1) and stillOK:#循环s1每个字符pos2 = 0found = Falsewhile pos2<len(alist) and not found:if s1[pos1]==alist[pos2]:#在s2逐个对比found=Trueelse:pos2 = pos2 + 1if found:alist[pos2] = None#找到,打勾else:stillOK = False#未找到,失败pos1 = pos1 + 1return stillOK
print(anagramSolution("abcd","dcba"))
- 问题规模:词中包含的字符个数n
- 主要部分在于两重循环:
外层循环遍历s1每个字符,将内层循环执行n次
而内层循环在s2中查找字符,每个字符的对比次数,分别是1、2…n中的一个,而且各不相同 - 所以总执行次数是1+2+3+…+n,可知数量级O(n2)
解法2:排序比较
- 思路:将两个字符串都按照字母顺序排好序,再逐个字符对比是否相同
def anagramSolution2(s1,s2):alist1 = list(s1)alist2 = list(s2) alist1.sort()alist2.sort()pos = 0matches = Truewhile pos<len(s1) and matches:if alist1[pos]==alist2[pos]:pos = pos + 1elsematches = Falsereturn matches
- 粗看上去,本算法只有一个循环,最多执 行n次,数量级是O(n)
但循环前面的两个sort并不是无代价的,如果查询下后面的章节,会发现排序算法采用不同的解决方案,其运行时间数量级差不多是 O ( n2 ) 或者O(n log n),大过循环的O(n). - 所以本算法时间主导的步骤是排序步骤
- 本算法的运行时间数量级就等于排序过程的数量级O(n log n)
解法3:暴力法
- 暴力法解题思路为:穷尽所有可能组合
- 将s1中出现的字符进行全排列,再查看s2是否出现在全排列列表中
- n个字符全排列,是n!个字符,例如,对于20个字符长的词来说,将产生 20!=2,432,902,008,176,640,000个候选词,如果每微秒处理1个候选词的话,需要近8万年时间来做完所有的匹配。所以我们就不用这个算法了,它不是个好算法。
解法4.计数比较
- 若两个字符中每个字母出现次数相同,则为变位词
- 具体做法:为每个词设置一个26位的计数 器,先检查每个词,在计数器中设定好每 个字母出现的次数,计数完成后,进入比较阶段,看两个字符 串的计数器是否相同,如果相同则输出是 变位词的结论
def anagramSolution4(s1,s2):c1 = [0]*26 #长度为26 全0的列表 代表每个字母出现的次数c2 = [0]*26for i in range(len(s1):pos = ord(s1[i])-ord('a') #ord返回字符的unicode编码 字母的编码是连续的c1[[pos] = c1[pos] + 1for i in range(len(s2):pos = ord(s2[i])-ord('a') #ord返回字符的unicode编码 字母的编码是连续的c2[[pos] = c2[pos] + 1j = 0stillOK = Truewhile j<26 and stillOK:#计数器比较if(c1[j]==c2[j]):j = j + 1else:stillOK = Falsereturn stillOK
- 前两个循环用于对字符串进行计数,操作次数等 于字符串长度n;第3个循环用于计数器比较,操作次数总是26次.
所以总操作次数T(n)=2n+26,其数量级为O(n)
这是一个线性数量级的算法,是4个变位词判断算法中性能最优的 - 本算法依赖于两个长度为26的计数器列表,来保存字符计数,这相比前3个算法需要更多的存储空间.(牺牲空间换时间)
4. Python数据类型的性能
- list和dict的常见操作
- list基本操作的大O数量级
- dict数据类型大O数量级
- 字典的执行时间与规模无关,是常数O(1)
而列表的执行时间则随着列表的规模加大,呈线性上升 O(n)
算法分析(python)相关推荐
- 资料分享:送你一本《数据结构与算法:Python语言描述》电子书!
下图为 TIOBE 3月编程语言排行榜. 从榜单来看,曾经铁打的 Java.C.C++ 局势,早已在数月前被 Python 的闯入而打破.究其根由,并非是 C++ 的应用领域正在逐渐缩减,而是随着人工 ...
- js rsa解密中文乱码_建议收藏 | 最全的 JS 逆向入门教程合集
点击上方"咸鱼学Python",选择"加为星标" 第一时间关注Python技术干货! 嘿,大家好,截止今天咸鱼零零散散分享爬虫.数据分析基础和 Web 的内容已 ...
- js滚动条下拉一定值_JS逆向 | 无限Debugger之淘大象
置顶公众号 今天继续和大家研究JS逆向,不少小伙伴在JS逆向的时候遇到过无限debugger的反爬,今天就拿一个网站练练手感受下无限debugger. 分析请求 先打开这次的目标网站--淘大象(htt ...
- 人工智能课程实训方案
第一章 发展背景 当今,世界无时无刻不在发生着变化.对于技术领域而言,普遍存在的一个巨大变化就是为大数据(Big data)打开了大门.随着国家大数据战略推进实施以及配套政策的贯彻落实,大数据产业发展 ...
- 京东APP中Flutter探索及优化
点击"开发者技术前线",选择"星标" 让一部分开发者先看到未来 前言 随着Flutter稳定版本逐步迭代更新,京东APP内部的Flutter业务也日益增多,Fl ...
- AI教学实训整体解决方案
第一章 发展背景 当今,世界无时无刻不在发生着变化.对于技术领域而言,普遍存在的一个巨大变化就是为大数据(Big data)打开了大门.随着国家大数据战略推进实施以及配套政策的贯彻落实,大数据产业发展 ...
- 高校人工智能专业实训建设方案
第一章 发展背景 当今,世界无时无刻不在发生着变化.对于技术领域而言,普遍存在的一个巨大变化就是为大数据(Big data)打开了大门.随着国家大数据战略推进实施以及配套政策的贯彻落实,大数据产业发展 ...
- python数据结构与算法分析_数据结构与算法(Python版)
为什么研究数据结构与算法 本周带大家进入Python版数据结构与算法的学习.想必大家都听过"算法"一词,算法的学习对编程者来说是至关重要的.首先我们先了解一下为什么要研究数据结构与 ...
- 【python数据挖掘课程】二十.KNN最近邻分类算法分析详解及平衡秤TXT数据集读取
这是<Python数据挖掘课程>系列文章,也是我这学期上课的部分内容及书籍的一个案例.本文主要讲述KNN最近邻分类算法.简单实现分析平衡秤数据集,希望这篇文章对大家有所帮助,同时提供些思路 ...
- python高斯求和_二、算法分析
一.什么是算法分析 程序和算法的区别: 算法是对问题解决的分步描述 程序是采用某种编程语言实现的算法,同一个算法通过不同的程序员采用不同的编程语言,能产生很多程序 算法分析的概念: 算法分析主要就是从 ...
最新文章
- 2020年AI将会如何发展?吴恩达、周志华、Yann LeCun等大神对2020年 AI 发展趋势的预测的预测...
- 持久对象生命周期的状态
- tmadmin: command not found和tmadmin: error while loading shared libraries: libgpnet.so
- STL 源代码分析 算法 stl_algo.h -- includes
- 新媒体运营工具大盘点,收藏方便不备之需!
- C++中数据类型int, short, long, long long的数据范围
- 二极管整流和同步整流区别
- Java计算某年某月天数_编程计算某年某月某日是该年的第多少天。例如:2016年3月2日是2016的 第62 天。(java)...
- JVM:垃圾收集器与内存分配策略
- 程序linux培训,马哥-51CTO-Linux培训-0910-程序包管理
- 2021,OpenSquare回顾过去,展望未来
- 小学教师听课体会 计算机,小学教师观有效课堂听课心得体会
- 数据中心的等级 数据中心的分层
- 电脑使用DP线连接显示器,插在显示器音频口的音响没有声音解决办法
- 《C++面向对象程序设计》董正言、张聪版内容概括
- 看门狗电路 通俗理解
- IIR数字滤波器设计---双线性变换法
- echarts绘制四川地图
- spark (3)Spark Standalone集群安装介绍
- 国,省,市,区(县)(四级联动)