-
2021-03-04 09:49:48
同一问题可用不同算法解决,而一个算法的质量优劣将影响到算法乃至程序的效率。算法分析的目的在于选择合适算法和改进算法。
算法复杂度分为时间复杂度和空间复杂度。其作用: 时间复杂度是度量算法执行的时间长短;而空间复杂度是度量算法所需存储空间的大小。
1、时间复杂度
1.1 时间频度
一个算法中的语句执行次数称为语句频度或时间频度。记为T(n)
1.2 时间复杂度
一般情况下,算法中基本操作重复执行的次数是问题规模n的某个函数,用T(n)表示,若有某个辅助函数f(n),使得当n趋近于无穷大时,T(n)/f(n)的极限值为不等于零的常数,则称f(n)是T(n)的同数量级函数。记作T(n)=O(f(n)),称O(f(n)) 为算法的渐进时间复杂度,简称时间复杂度。
在各种不同算法中,若算法中语句执行次数为一个常数,则时间复杂度为O(1),另外,在时间频度不相同时,时间复杂度有可能相同,如 T(n)=n2+3n+4与T(n)=4n2+2n+1它们的频度不同,但时间复杂度相同,都为O(n2)。
按数量级递增排列,常见的时间复杂度有:常数阶O(1),对数阶O(log2n),线性阶O(n), 线性对数阶O(nlog2n),平方阶O(n2),立方阶O(n3),..., k次方阶O(nk),指数阶O(2n)。
随着问题规模n的不断增大,上述时间复杂度不断增大,算法的执行效率越低。
2、空间复杂度
一个算法的空间复杂度(Space Complexity)S(n)定义为该算法所耗费的存储空间,它也是问题规模n的函数。渐近空间复杂度也常常简称为空间复杂度。
一个算法在计算机存储器上所占用的存储空间,包括存储算法本身所占用的存储空间,算法的输入输出数据所占用的存储空间和算法在运行过程中临时占用的存储空间这三个方面。算法的输入输出数据所占用的存储空间是由要解决的问题决定的,是通过参数表由调用函数传递而来的,它不随本算法的不同而改变。存储算法本身所占用的存储空间与算法书写的长短成正比,要压缩这方面的存储空间,就必须编写出较短的算法。算法在运行过程中临时占用的存储空间随算法的不同而异,有的算法只需要占用少量的临时工作单元,而且不随问题规模的大小而改变
一个算法的空间复杂度只考虑在运行过程中为局部变量分配的存储空间的大小,它包括为参数表中形参变量分配的存储空间和为在函数体中定义的局部变量分配的存储空间两个部分。若一个算法为递归算法,其空间复杂度为递归所使用的堆栈空间的大小,它等于一次调用所分配的临时存储空间的大小乘以被调用的次数(即为递归调用的次数加1,这个1表不开始进行的一次非递归调用)。算法的空间复杂度一般也以数量级的形式给出。如当一个算法的空间复杂度为一个常量,即不随被处理数据量n的大小而改变时,可表示为O(1);当一个算法的空间复杂度与以2为底的n的对数成正比时,可表示为0(10g2n);当一个算法的空I司复杂度与n成线性比例关系时,可表示为0(n).若形参为数组,则只需要为它分配一个存储由实参传送来的一个地址指针的空间,即一个机器字长空间;若形参为引用方式,则也只需要为其分配存储一个地址的空间,用它来存储对应实参变量的地址,以便由系统自动引用实参变量。
对于一个算法,其时间复杂度和空间复杂度往往是相互影响的。当追求一个较好的时间复杂度时,可能会使空间复杂度的性能变差,即可能导致占用较多的存储空间;反之,当=i自求一个较好的空间复杂度时,可能会使时间复杂度的性能变差,即可能导致占用较长的运行时间。另外,算法的所有性能之间都存在着或多或少的相互影响。因此,当设计一个算法(特别是大型算法)时,要综合考虑算法的各项性能,算法的使用频率,算法处理的数据量的大小,算法描述语言的特性,算法运行的机器系统环境等各方面因素,才能够设计出比较好的算法。
更多相关内容 -
Java 时间复杂度和空间复杂度
2022-04-16 21:05:21时间复杂度的定义:在计算机科学中,算法的时间复杂度是一个函数,它定量描述了该算法的运行时间。一个算法执行所耗费的时间 大O渐近表示法 计算时间复杂度和空间复杂度时,为了估算一个算法的耗时情况,不需要计算...1.算法效率
算法效率分析分为两种:第一种是时间效率,第二种是空间效率。时间效率被称为时间复杂度,而空间效率被称作空间复杂度。 时间复杂度主要衡量的是一个算法的运行速度,而空间复杂度主要衡量一个算法所需要的额外空间
2.时间复杂度
时间复杂度的定义:在计算机科学中,算法的时间复杂度是一个函数,它定量描述了该算法的运行时间。一个算法执行所耗费的时间
大O渐近表示法
计算时间复杂度和空间复杂度时,为了估算一个算法的耗时情况,不需要计算出精确的执行次数,只需要计算到一个大概的计算次数次数即可,我们使用大O渐近表示法
O()->是一个函数渐近的数学符号
1.常数1表示所有的加法常数 1000或者10000只保留1
2.最后的大O函数只保留最高项,N^ 2+N+100只保留N^2
3.若最高阶还有系数,去除系数,3N^ 2或者2N^ 2只保留N^2此时一共执行次数为:N^2+2N+10
时间复杂度:O(N^2)
此时执行次数:N+M,由于无法判断N和M的大小,所以时间复杂度:O(N+M)
此时执行次数100次,时间复杂度:O(1)千万看到有N就是O(N)
这个算法在下一次循环时起始位置或者末位置就变成了区间的一半,每次变为原先的一半,执行次数:O(logN)
任意算法,如果不断/任意数字,最终等于1或者0,这个算法的时间复杂度就是O(logN)
一个算法能做到对数级别那么一定是一个优秀的算法一个递归函数的时间复杂度,要展开这个递归函数,看递归了多少次
int fun6(int n) { return n<2?n:fun6(n-1)*n; }
一共递归了n-1次,这个算法的时间复杂度O(n)
斐波那契函数的递归
int fun7(int n) { return n<2?1:fun7(n-1)+fun7(n-2); }
计算这个递归函数的时间复杂度比较特殊,递归次数是二叉树的结点个数2^n -1
时间复杂度为O(2^n)重点掌握O(1)O(n)O(n^2)O(logn)O(nlogn)
最坏情况的时间复杂度:这个算法的最大运行时间
最好情况的时间复杂度:这个算法的最小运行时间
平均情况的时间复杂度:这个算法的平均运行时间
当前数组的个数为n,从头开始遍历,如果所需的元素在末尾就是最坏情况的时间复杂度O(n),如果所需的元素在第一个就是最好情况的时间复杂度O(1),如果所需的元素在中间就是O(n/2)3.空间复杂度
所谓空间复杂度指的是算法中”额外”开辟的内存空间
计算空间复杂度也使用大O渐近法
一般来说空间复杂度就看算法中有没有开辟”数组”空间
像这种没有额外开辟内存的就是O(1)long[] fun8(int n) { long[] arr = new long[n+1];//在堆开辟了一个长度为n+1的数组就是O(n) arr[0] =0; arr[1] = 1; for (int i = 2; i < n; i++) { arr[i] = arr[i-1]+arr[2]; } return arr; }
开辟了一个长度为n+1的数组就是O(n)
当只定义了几个临时变量,O(1)
定义了一些变量,而且这些变量的个数与N有关
int[] data = new int[n] => O(n)递归函数每次函数调用过程,就对应一个函数的”栈帧”在栈中的入栈过程,递归函数调用几次,就需要开辟多少个栈帧空间
这个递归函数递归了n-1次,空间复杂度:O(n)void fun9(int n) { if(n==1) { return; } int[] arr = new int[n]; fun9(n-1); }
这个递归函数会调用n次,每次调用开辟一个长度为n的数组
空间复杂度:O(n^2) -
Java时间复杂度和空间复杂度
2021-11-03 10:23:452. 时间复杂度 2.1 时间复杂度的概念 2.2 大 O 的渐进表示法 3. 空间复杂度 1. 算法效率 算法效率分为两种,一种是时间效率,一种是空间效率,时间效率又称时间复杂度,空间效率又称空间...1. 算法效率
2. 时间复杂度
2.1 时间复杂度的概念
2.2 大 O 的渐进表示法
3. 空间复杂度
1. 算法效率
算法效率分为两种,一种是时间效率,一种是空间效率,时间效率又称时间复杂度,空间效率又称空间复杂度。时间复杂度主要衡量的是一个算法的运行速度,而空间复杂度主要衡量的是算法额外需要的运行空间。在计算机才初步发展的年代,计算机的存储容量非常小,人们对算法空间复杂度的重视程度远远大于时间复杂度,但随着计算机技术的迅速发展,计算机的内存容量已经有了非常大的提高,所以现在我们对算法的时间复杂度的关注程度更高。
2. 时间复杂度
2.1 时间复杂度的概念
在计算机科学中,算法的时间复杂度是一个函数,它定量描述了算法的运行时间。从理论上来说,一个算法的运行时间是不能算出来的,只有将程序运行起来才能知道运行时间,而且同一个程序在不同的环境内运行时间也有可能不同,何况如果我们每个程序通过上机测试来查找运行时间,那也太麻烦了一些,于是,我们引入了时间复杂度这个概念。
一个算法的时间复杂度指的是算法中基本操作的执行次数。2.2 大 O 的渐进表示法
分析一下func1()方法中循环操作执行了多少次
void func1(int N){ int count = 0; for (int i = 0; i < N ; i++) { //双重循环共执行n*n次 for (int j = 0; j < N ; j++) { count++; } } for (int k = 0; k < 2 * N ; k++) { //单重循环共执行2*n次 count++; } int M = 10; while ((M--) > 0) { //单重循环共执行10次 count++; } System.out.println(count); }
func1()共执行的基本操作次数:
F(N) = N^2 + 2*N + 10
当 N=10时,F(N)=130
当 N=100时,F(N)=10210
当 N=1000时,F(N)=1002010实际中我们计算时间复杂度时,其实并不一定要计算精确的执行次数,而只需要大概执行次数,那么就可以采用大 O 的渐进表示法。
大O符号(Big O notation):是用于描述函数渐进行为的数学符号。
推导大O阶方法:
1、用常数1取代运行时间中的所有加法常数。
2、在修改后的运行次数函数中,只保留最高阶项。
3、如果最高阶项存在且不是1,则去除与这个项目相乘的常数。得到的结果就是大O阶。使用大 O 的渐进表示法后,func1()的时间复杂度为: O(N^2)
当N = 10时,F(N) = 100
当N = 100时, F(N) = 10000
当N = 1000时, F(N) = 1000000通过上面我们会发现大O的渐进表示法去掉了那些对结果影响不大的项,简洁明了的表示出了执行次数。
另外有些算法的时间复杂度存在最好、平均和最坏情况:
最坏情况:任意输入规模的最大运行次数(上界)
平均情况:任意输入规模的期望运行次数
最好情况:任意输入规模的最小运行次数(下界)
例如:在一个长度为N数组中搜索一个数据x
最好情况:1次找到
最坏情况:N次找到
平均情况:N/2次找到在实际中一般情况关注的是算法的最坏运行情况,所以数组中搜索数据时间复杂度为O(N)
3. 空间复杂度
空间复杂度是对一个算法在运行过程中临时占用存储空间大小的量度 。空间复杂度不是程序占用了多少bytes的空间,这样计算并无意义,所以空间复杂度算的是变量的个数。
空间复杂度计算规则与时间复杂度类似,也使用大O渐进表示法。
实例一:
// 计算bubbleSort的空间复杂度? void bubbleSort(int[] array) { for (int end = array.length; end > 0; end--) { boolean sorted = true; for (int i = 1; i < end; i++) { if (array[i - 1] > array[i]) { Swap(array, i - 1, i); sorted = false; } } if (sorted == true) { break; } } }
使用了常数个额外空间,所以空间复杂度为 O(1)
实例二:
// 计算fibonacci的空间复杂度? int[] fibonacci(int n) { long[] fibArray = new long[n + 1]; fibArray[0] = 0; fibArray[1] = 1; for (int i = 2; i <= n ; i++) { fibArray[i] = fibArray[i - 1] + fibArray [i - 2]; } return fibArray; }
动态开辟了N个空间,空间复杂度为 O(N)
实例三:
// 计算阶乘递归Factorial的时间复杂度? long factorial(int N) { return N < 2 ? N : factorial(N-1)*N; }
递归调用了N次,开辟了N个栈帧,每个栈帧使用了常数个空间。空间复杂度为O(N)
-
java时间复杂度计算
2021-03-13 01:14:04时间复杂度是指算法执行语句执行的次数。常见的时间复杂度有以下几种:描述时间复杂度常数阶O(1)对数阶O(logn)线性阶O(n)线性对数阶O(nlogn)平方阶O(n²)立方阶O(n³)n次方阶O(mⁿ)指数阶O(2ⁿ)阶乘阶O(n!)(1) O(1)O...时间复杂度是指算法执行语句执行的次数。
常见的时间复杂度有以下几种:
描述
时间复杂度
常数阶
O(1)
对数阶
O(logn)
线性阶
O(n)
线性对数阶
O(nlogn)
平方阶
O(n²)
立方阶
O(n³)
n次方阶
O(mⁿ)
指数阶
O(2ⁿ)
阶乘阶
O(n!)
(1) O(1)
O(1)是常量级时间复杂度的一种表示方法,并非只执行一行代码。
代码执行时间不是随着n的增大而增大,这样的代码的时间复杂度都是O(1)。
注意:通常只要算法中不存在循环、递归,即使代码有很多行,时间复杂度仍是O(1)
(2) O(logn)、O(nlogn)对数阶时间复杂度
int i = 1;
while(i<=n){
i=i*2;
}
代码line3是执行次数最多的,只要算出第3行执行的次数,它代表的就是整个代码的时间复杂度。i从1开始取值,每一次循环乘以2。可以看到 i=i*2是一个等比数列,即:2º 2¹ 2² ...... 2^k = n。只要算出k是多少,就是执行的次数了 2^k=n -->k=log2n,所以时间复杂度应该为O(log2n)。
int i = 1;
while(i<=n){
i=i*5;
}
很容易就能看出来,应该是O(log5n)。但是上面的O(log2n)和O(log5n)可以通过换底公式换成以2为底的对数,且可以忽略系数,所以都记做 O(logn)。
关于O(nlogn),就是把上面的代码在循环执行n遍了。其中归并排序、快速排序的时间复杂度就是O(nlogn)
(3)O(m+n)、O(m*n)
1. 加法法则(量级最大法则):总复杂度等于量级最大的那段代码的复杂度。
public static Integer getSum(Integer n){
int sum1 = 0;
int sum2 = 0;
for (int i = 0; i < 1000; i++){
sum1 += i;
}
for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
sum2 += i*j;
}
}
return sum1 + sum2;
}
sum1和sum2分别是 O(n)和O(n²),对于这三个,我们取量级最大的O(n²),所以总的时间复杂度就等于量级最大的那段代码的时间复杂度。
2.乘法法则:嵌套代码的复杂度等于嵌套内外代码复杂度的乘积 。
public static Integer getSum(Integer n){
int sum = 0;
for (int i = 0; i < n; i++){
sum += func(i);
}
return sum;
}
public static Integer func(Integer x){
int sum = 0;
for (int i = 0; i < x; i++){
sum += i^2;
}
return sum;
}
func()函数的时间复杂度是 T1(n)=O(n),如果先把func()函数看成简单的操作,则getSum()函数的时间复杂度是T2(n)=O(n),所以整个getSum()函数的时间复杂度是T(n)=T2(n)*T1(n)=O(n*n)=O(n^2)
3.循环不仅与n有关,还与执行循环所满足的判断条件有关。
public static Integer func(Integer x, Integer[] arr){
int sum = 0;
int i=0;
while (i < x && arr[i]!=1)
{
i++;
sum += arr[i];
}
return sum;
}
在此循环,如果arr[i]不等于1的话,时间复杂度是O(n)。如果arr[i]等于1的话,则循环执行一次判断跳出,时间复杂度是O(1)。
常见算法的时间复杂度以及空间复杂度如下:
附:
链表实现与时间复杂度分析
数组算法时间复杂度
红黑树的插入和遍历时间复杂度分析
-
Java时间复杂度的比较
2022-01-20 21:16:11O(1) 越复杂,耗费的时间越多 -
JAVA 时间复杂度和空间复杂度
2019-10-23 15:13:16算法的时间复杂度 定义:在进行算法分析时,语句总的执行次数T(n)是关于问题规模n的函数,进而分析T(n)随n的变化情况并确定T(n)的数量级。算法的时间复杂度,记作T(n)=O(f(n)),它表示随着问题规模n的增大,算法时间... -
Java时间复杂度和空间复杂度分析
2018-09-28 11:38:11(分析时间复杂度及空间复杂度) 迭代算法 #define _CRT_SECURE_NO_WARNINGS #include<stdio.h> #include<string.h> #include<assert.h> ... -
Java的时间复杂度和空间复杂度
2022-03-28 13:37:25时间复杂度2.1 时间复杂度的概念2.2 大O的渐进表示法3.空间复杂度 1.算法效率 算法效率分析分为两种:第一种是时间效率,第二种是空间效率。时间效率被称为时间复杂度,而空间效率被称作空间复杂度。 时间复杂度主要... -
java时间复杂度和空间复杂度详解
2021-02-07 19:08:10结果三、时间复杂度介绍四、计算时间复杂度的方法1.方法2.示例五、时间复杂度分析1.分析算法中的时间复杂度2.结果六、常见的时间复杂度1.常数阶O(1)2.对数阶O(log~2~n)3.线性阶O(n)4.线性对数阶O(nlog~2~n)5.平方阶O... -
排序算法时间复杂度的分析java语言描述
2018-12-01 18:11:09选择排序、冒泡排序、归并排序、快速排序、插入排序的算法原理。不同排序算法时间效率的经验分析方法,验证理论分析与经验分析的一致性。 -
Java~时间复杂度和空间复杂度详解
2022-03-12 21:46:21时间复杂度 常见时间复杂度计算举例 空间复杂度 常见空间复杂度计算举例 算法效率 如何去衡量一个算法的好坏? 通常我们从时间效率和空间效率两个方面去分析算法的好坏。时间效率即时间复杂度,空间效率被... -
01.Java-时间复杂度
2021-03-07 09:33:58时间复杂度1、时间频度时间复杂度通常是衡量算法的优劣的,衡量算法的时间严格来讲是很难衡量的,由于不同的机器性能不用环境都会造成不同的执行时间。算法的执行时间和语句的执行次数成正比,因此通过计算执行测试... -
Java——时间复杂度、空间复杂度详解
2021-11-03 17:03:48复杂度算法效率时间复杂度什么是时间复杂度推导大 O 阶的方法算法情况计算冒泡排序的时间复杂度计算二分查找的时间复杂度计算阶乘递归的时间复杂度计算斐波那契递归的时间复杂度?空间复杂度计算冒泡排序的空间... -
Java-时间复杂度&空间复杂度
2020-09-22 17:02:45时间复杂度&空间复杂度 一、时间复杂度 1、时间复杂度:执行算法所消耗的时间; 2、时间复杂度计算方式 (1)定义理解:“执行算法所消耗的时间”,但是不能采用让算法跑一遍来计算其时间复杂度。 Reason1:受... -
JAVA之时间复杂度和空间复杂度(图解)
2021-11-01 22:44:25时间效率被称为时间复杂度,而空间效率被称作空间复杂度。 时间复杂度主要衡量的是一个算法的运行速度,而空间复杂度主要衡量一个算法所需要的额外空间,在计算机发展的早期,计算机的存储容量很小。所以对空间... -
java排序时间的时间复杂度和空间复杂度说明(png)
2019-05-24 09:14:45对java的8种排序方法的空间复杂度和时间复杂度,进行了一个简单的统计 -
Java-时间复杂度和空间复杂度的概念和计算
2021-05-02 18:19:31文章目录一、算法效率二、时间复杂度1.时间复杂度的概念2.大O的渐进表示法(1)推导大O阶方法3.时间复杂度的三种情况(1) 最坏情况(2)最好情况(3)平均情况4.常见时间复杂度计算举例1.例子2.冒泡排序时间复杂度3.二分... -
java方法时间复杂度计算
2019-11-23 17:00:14时间复杂度是指 算法执行语句执行的次数。 常见的时间复杂度有以下几种: 描述 时间复杂度 常数阶 O(1) 对数阶 O(logn) 线性阶 O(n) 线性对数阶 O(nlogn) 平方阶 O(n²) 立方阶 O(n³) n次方阶 ... -
时间复杂度
2021-03-05 23:23:14ArrayList部分一共五篇文章了,并且引入了时间复杂度来分析,强烈建议大家一定要按顺序阅读,相关文章分别是:最近看了一下评论区里,大家都急着想要了解HashMap,先不要着急,要完整的了解HashMap的内部实现,我们... -
java排序 时间复杂度 空间复杂度 稳定性的总结
2022-02-04 11:57:24时间复杂度 : O(N^2) 空间复杂度 : O(1) 稳定性 : 无 冒泡 时间复杂度 : O(N^2) 空间复杂度 : O(1) 稳定性 : 有 插入 时间复杂度 : O(N^2) 空间复杂度 : O(1) 稳定性 : 有 归并 时间复杂度 : O(N * logN) 空间复杂度... -
java时间复杂度
2018-12-17 14:09:26O(1)是常量级时间复杂度的一种表示方法,并非只执行一行代码 代码执行时间不是随着n的增大而增大,这样的代码的时间复杂度都是O(1) 通常只要算法中不存在循环、递归,即使代码有很多行,时间复杂度仍是O(1) ... -
java快速排序及时间复杂度
2021-12-04 10:20:15快速排序是通过递归,来排序的,先定义一个...=j) { while(arr[j]>=base&&i 结果如下图: 时间复杂度:递归的时间复杂度是O(logn),交换是o(1),但游标移动的时间复杂度是o(n),所以总体来说时间复杂度是O(nlogn) -
算法时间复杂度的计算方法
2021-04-23 11:54:231. 时间复杂度时间复杂度是指程序运行从开始到结束所需要的时间。时间复杂度的计算一般比较麻烦,故在数据结构的研究中很少提及时间复杂度。为了便于比较同一个问题的不同算法,通常做法是,从算法中选取一种对于所... -
二分查找(折半查找)java及时间复杂度分析
2022-04-06 14:59:11前提是元素是有序排列的。指定要查找的k值。 找到了就返回k的下标,没有...时间复杂度为 O(log2(n))。 java代码如下: public class BinarySearch { public static int binary(int a[],int k) { int low = 0; -
java测试程序时间复杂度
2020-10-11 11:10:57之前做算法题就是提交到算法相关平台上查看运行结果和时间复杂度,这样测试的缺点是:只能测试算法平台给出的算法题目,如果想测试自己的随便一段代码就走不通了。 但其实测试程序的时间复杂度很简单,只需要在想... -
时间复杂度计算和举例说明
2021-04-24 12:28:06时间复杂度一般情况下,算法中的基本操作语句的重复执行次数是问题规模n的某个函数,用T(n)表示,若有某个辅助函数f(n),使得当n趋近于无穷大时,T(n) / f(n)的极限值为不等于零的常数,则称f(n)是T(n)的同数量级...