繁体   English   中英

关于大O符号和复杂性

[英]About Big O Notations and Complexity

我目前正在学习Big O Notations,但是我根据不同的复杂性对时间/迭代计算感到困惑。

我解决了这个问题:

每次测试都需要10 ^( - 7)秒的算法。 如果解决方案的数量是以下函数:logn,n,nlog。 n ^ 2,我可以计算的最大n是多少,例如,小于1秒?

我所关注的(对于案例登录)是10 ^ -7次登录必须花费不到1秒:

10^(-7) * logn < 1 <=> n = 10^(1/10^-7)

令人难以置信的大(如果没错,哦,该死的 - ')。 但是n ^ 2怎么样?

10^(-7) * n^2 < 1 <=> n = square_root(1/10^-7)

但是,如果复杂度更大,n ^ 2情况下的解决方案数量如何能够小于n中的数量? 这让我很困惑......?

“这在很多层面都很糟糕。”

首先,O(f(n))与f(n)不同。

复杂性通常用于表示解决问题所需的时间 ,作为输入大小的函数。

当然,如果你可以使用X对Y在相同的时间内解决更多的问题,X将在固定的时间内解决比Y更多的问题。但是由于你没有以正确的方式使用术语复杂性,它是毫不奇怪,你得到一个(看似)矛盾的答案。

您只需将算法上限限制为10 ^( - 7)秒的实际世界时间,这意味着您的算法将保证在10 ^( - 7)秒内完成所有复杂性。

让我们不要讨论这是否可能实际存在。 但是,由于您刚刚定义了算法以通过10 ^( - 7)中的所有可能解决方案 ,这意味着无论n是什么,它都将在那个时间内完成。 所以你的n是正无穷大。

此外,我认为你不应该使用大O来表示解决方案的数量

好消息首先,计算结果没有“错误”。

当然,如果算法的复杂性更高(如O(n ^ 2)复杂度高于O(log n)),那么在“可接受”时间内仍然能够处理的问题的大小将会更小,总计根据你的计算。

然而这个例子似乎有点扭曲,我不得不承认,我没有完全理解目的,你发明了10 ^ -7因子,因此怀疑,你没有得到O符号的概念。

基本上O符号的主要思想是,在比较两种算法时,你并不关心任何线性因素(比如你在计算中发明的10 ^ 7因子),而只关心计算时间随着大小的增长而增长的速度。问题是,由于问题的大小,与计算时间的增长相比,因为不变(因此不会增长)因素迟早会变得无关紧要。

以身作则:

使用O(n ^ 2)算法A,花费时间t = 2 * n ^ 2毫秒和O(log n)算法B,对于给定的问题大小,在特定机器上取t = 200 * log(n)毫秒事情看起来如下:

对于一个非常小的问题,比如n = 10,算法A可能比算法B更快:

2*10^2 = 2*100 = 200 ms
400*log10 = 400*1 = 400 ms

但随着问题规模越来越大,比如n = 100,算法B迟早会在速度上超过算法A:

2*100^2 = 2*10,000 = 20,000 ms
400*log100 = 400*2 = 800 ms

虽然对于更大的问题规模,比如n = 1,000,000,等待A完成可能需要很大的耐心。

2*1,000,000^2 = 2*10^12 ms = 2*10^9 s = 33333333 min = 555555 h = 23148 days = 63 years

算法B可能仍然在可接受的时间内运行。

400*log1,000,000 = 400*6 = 2,400 ms = 2.4 s

随着问题规模不断扩大,常数因素扮演着越来越小的角色,对于越来越大的问题,它变得越来越无关紧要,因此(与低阶条款一致,遵循相同的规则)在O符号中被遗漏。

因此,以O符号给出的复杂性的“正确”方式不是试图查看固定n的固定值,或者甚至重新发明常数因子和已经抽象出来的低阶附加项,而是看看计算时间有多快会随着问题而增长尺寸。

因此,再次以示例的方式来看待O(n ^ 2)和O(log10)的复杂性的“正确”方法是比较它们的增长。

如果问题大小增加10倍算法A的计算时间将增加100倍,因此需要100倍的时间,如下:

(n*10)^2 = n^2 * 10^2 = n^2 * 100

虽然算法B的计算时间只会增长一倍,但是:

log(n*10) = log(n) + log(10) = log(n) + 1

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM