时间复杂度与O(n)

1 复杂度分析

1.1 时间复杂度

​ 时间复杂度用来表示算法运行时间的长短,用来定性的描述程序的运行时间。要了解时间复杂度,我们需要先了解程序执行的次数。

1.1.1 循环执行次数

(1)

for (int i=0; i<n; i++)
{
  printf("%d\n", i);
}
//该代码段内,for() 语句将被执行 n+1 次,而不是 n 次,当 i=n-1 时,循环正常运行,当 i=n 时,for() 仍需要判断 i<n 条件是否成立,不成立,跳出 for() 循环,最后一次判断导致 for() 语句的执行次数是 n+1 次,而不是 n 次。

//printf()只有在符合 i<n 条件时,才会执行printf语句,所以执行次数为n,而不是n+1。

(2)

for (int i=0; i<n; i++)
{   
	for (int j=0; j<n; j++)
	{
    printf("i:%d,j:%d\n", i ,j);
	}  
} 
//该代码段内,for(i=0, i<n, i++)外部循环语句将执行 n+1 次。for(j=0 , j<n, j++)将被执行 n(n+1) 次。

//printf()将执行 n*n 次。

(3)

for (i=1; i<=n; i++)
{   
	for (j=1; j<=i; j++)
	{
		for (k=1; k<=j; k++)   
    {
      printf("i:%d, j:%d, k:%d \n", i, j , k);  
    }
	}  
} 
//该代码段内,从内到外思考 printf() 的循环次数,内部第一层循环执行 j 次,第二层循环,执行次数是 j 分别取值 0~i 的求和。可得 printf() 的执行次数为:

∑ i = 1 i = n ∑ j = 1 j = i j = 1 / 6 n ( n + 1 ) ( 2 n + 1 ) \sum_{i=1}^{i=n}\sum_{j=1}^{j=i} j = 1/6n(n+1)(2n+1) i=1i=nj=1j=ij=1/6n(n+1)(2n+1)

这里有些小伙伴会疑惑,为什么就成累加了呢?我们只考虑内部的 j 和 k 两层循环,带入具体的值想一下:

​ 假设 j 的最大值是5,j 会从 1 一直累加到 5 ,那么 j = 1 时,k <= 1,此时printf会被执行一次,之后内部循环就不满足循环条件退出了,而外部循环中的 j 就被累加到了 2 ,此时 k <= 2,此时printf会被执行两次,然后跳出循环,以此类推,执行的次数就是 1+ 2 + 3+ 4 + 5。

(4)

for (i=1; i<=n; i=i*2)
{
  printf("Hello World\n");
}

//该代码段内,i=i*2 我们设执行次数为k,所以跳出循环的判断条件可以简化表示为:

2 k − 1 > n 即 k = l o g 2 ( n + 1 ) 2^k-1 > n 即 k = log_2 (n+1) 2k1>nk=log2(n+1)

1.1.2 大O(n)表示法

(1)对于以上四个循环例子,当 n 趋于无限大时,执行次数的系数和常数项可以忽略不计,因此,以上四个例子的 printf() 语句的时间复杂度用 O(n) 可以表示为:

  1. O ( n ) O(n) O(n)

  2. O ( n 2 ) O(n^2) O(n2)

  3. O ( n 3 ) O(n^3) O(n3)

  4. O ( l o g 2 ( n ) ) O(log_2 (n)) O(log2(n))

(2)常见的时间复杂度,以及当 n 区域无穷大时的效率:

在这里插入图片描述

(3)在用 O(n) 描述算法的时间复杂度时,我们往往一般说的是平均时间复杂度,除此之外,我们还需要考虑,最差时间复杂度,和最好时间复杂度。

1.2 空间复杂度

​ 即算法占用内存空间的大小。与时间复杂度不同,我们通常只关注最差空间复杂度。因为内存空间是硬性要求,我们必须确保在所有输入数据下都有足够的内存空间预留。

空间复杂度的推算方法与时间复杂度大致相同,只需将统计对象从 “操作数量” 转为 “使用空间大小” 我们举几个例子。

  1. O ( 1 ) :与循环无关的变量 O(1):与循环无关的变量 O(1):与循环无关的变量

  2. O ( l o g 2 ( n ) ) :例如递归树,分治算法 O(log_2 (n)):例如递归树,分治算法 O(log2(n)):例如递归树,分治算法

  3. O ( n ) :例如数组,链表,栈,队列 O(n):例如数组,链表,栈,队列 O(n):例如数组,链表,栈,队列

  4. O ( n 2 ) :例如二维数组 O(n^2):例如二维数组 O(n2):例如二维数组

  5. O ( l o g 2 ( n ) ) :例如二叉树 O(log_2 (n)):例如二叉树 O(log2(n)):例如二叉树

  • 24
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值