赞
踩
给大黄一条长10寸的面包,大黄每3天吃掉1寸,那么吃掉整个面包需要几天?
给大黄一条长16寸的面包,大黄每5天吃掉面包剩余长度的一半,第一次吃掉8寸,第二次吃掉4寸,第三次吃掉2寸…那么大黄把面包吃得只剩下1寸,需要多少天呢?
给大黄一条长10寸的面包和一个鸡腿,大黄每2天吃掉一个鸡腿。那么大黄吃掉整个鸡腿需要多少天呢?
给大黄一条长10寸的面包,大黄吃掉第一个一寸需要1天时间,吃掉第二个一寸需要2天时间,吃掉第三个一寸需要3天时间…每多吃一寸,所花的时间也多一天。那么大黄吃掉整个面包需要多少天呢?
上面所讲的是吃东西所花费的相对时间,这一思想同样适用于对程序基本操作执行次数的统计。刚才的四个场景,分别对应了程序中最常见的四种执行方式
场景1: T(n) = 3n,执行次数是线性的
void eat1(int n){
for(int i=0; i<n; i++){;
System.out.println("等待一天");
System.out.println("等待一天");
System.out.println("吃一寸面包");
}
}
场景2: T(n) = 5logn,执行次数是对数的
void eat2(int n){
for(int i=1; i<n; i*=2){
System.out.println("等待一天");
System.out.println("等待一天");
System.out.println("等待一天");
System.out.println("等待一天");
System.out.println("吃一半面包");
}
}
场景3: T(n) = 2,执行次数是常量的
void eat3(int n){
System.out.println("等待一天");
System.out.println("吃一个鸡腿");
}
场景4: T(n) = 0.5n^2 + 0.5n,执行次数是一个多项式
void eat4(int n){
for(int i=0; i<n; i++){
for(int j=0; j<i; j++){
System.out.println("等待一天");
}
System.out.println("吃一寸面包");
}
}
有时候复杂度会受其他数据的影响,会有最坏时间复杂度、平均时间复杂度、最好时间复杂度,一般情况下,只考虑最坏时间复杂度和平均时间复杂度
对于复杂的算法,可以将其分为几个容易估算的部分,然后利用大 O 加法法则和乘法法则,计算算法的复杂度:
场景1:
T(n) = 3n
最高阶项为3n,省去系数3,转化的时间复杂度为:T(n) = O(n) 大 O 线性阶
场景2:
T(n) = 5logn
最高阶项为5logn,省去系数5,转化的时间复杂度为:T(n) = O(logn) 大 O 对数阶
场景3:
T(n) = 2
只有常数量级,转化的时间复杂度为:T(n) = O(1) 大 O 常数阶
场景4:
T(n) = 0.5n^2 + 0.5n
最高阶项为 0.5n^2,省去系数0.5,转化的时间复杂度为:T(n) = O(n^2) 大 O 平方阶
大O表达式 | 算法的好坏 |
---|---|
O(1) | 最好 |
O(logn) | 比较好 |
O(n) | 良好 |
O(n^2) | 不好 |
O(n^3) | 很不好 |
O(2^n) | 很很不好 |
O(n!) | 最不好 |
例子:
空间复杂度和时间复杂度很类似,当一个算法的空间复杂度为一个常量,即不随被处理数据量 n 的大小而改变时,可表示为 O(1);当一个算法的空间复杂度与以2为底的 n 的对数成正比时,可表示为 O(log2n);当一个算法的空间复杂度与 n 成线性比例关系时,可表示为O(n)…
程序的设计中要不就是时间换空间,要不就是用空间去换时间。并且时间和空间是可以进行相互转化的:
//时间换空间
int a = 5;
int b = 10;
a = a+b;//得到a值为15
b = a-b;//得到b值为5
a = a-b;//得到a值为10
//空间换时间
int c = 5;
int d = 10;
int e = c;//得到e为5
c= d;//得到c值为10
d= e;//得到d值为
结论:
在程序当中,请求分页,请求分段,都属于用时间去换空间。在项目当中使用各种缓存技术,都属于利用空间去换时间。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。