【问题标题】:Is the measurement of the big O notation correct in my algorithm?我的算法中大 O 符号的测量是否正确?
【发布时间】:2018-02-21 16:03:22
【问题描述】:

Here is the link to algorithm without comments, to see better

function getLastFactor(n) {
 var tempArr = [2, 3], max = Math.sqrt(n); /* (1 + 1) 
 it is despised
 */
 for(var i = 5; i < max; i += 2) { /* 
 (sqrt(n) - 5)  ---> ( 5 is despised )
 */
  if(n%i) continue; /* 
  sqrt(n) - 5 operations 
  PD: Should I add this? or is it already included in the for, in (sqrt(n) - 5 above) ?
 */
  if(check(tempArr, i)) continue; // How do I measure this? If I do not have security of the number?
  tempArr.push(i); // 1 operation it is despised
 }
 return tempArr[tempArr.length - 1]; // 1 operation
}

function check(array, i) {
 for(var j = 0, l = array.length; j < l; ++j) { // sqrt(n) operations 
  var cur = array[j]; // 1 operation
  if(!(i%cur)) return true; // 1 operation
 }
 
// O(3 * sqrt(n))

我不知道真正加起来是什么,我读过这并不重要,因为Big O 符号将其标准化,消除了次要顺序的条款。但我有很多疑问,比如我在代码本身中留下的一些疑问,还有:

  • 1) 我应该计算依赖条件的操作吗? ,想象一下我有一个条件,如果你判断为真,会做一个循环来提高n次操作的效率,这个应该考虑到,因为它会造成很大的变化。

  • 2)我认为这段代码的效率是O (sqrt (n) * 3),这样对吗?

这个问题不是重复的,我通过网络阅读了很多,尤其是在这个社区,几乎所有的问题/答案都是基于理论的,几乎从未见过理论和实践的例子同时出现时间。

【问题讨论】:

    标签: algorithm time-complexity big-o


    【解决方案1】:

    首先,当使用 big-o 表示法时删除所有常量,所以O (sqrt (n) * 3) 实际上是O (sqrt (n))

    为了正确分析这段代码的渐近复杂度,我们需要一些数论背景。这个算法基本上执行的是确定n 的主要因素(只返回最大的)。程序的主要部分是一个for 循环,它遍历从5sqrt(n) 的所有奇数,所以迭代次数是(sqrt(n) - 5) / 2,或者用big-o 术语来说,O(sqrt(n))

    接下来,有一个语句if(n%i) continue; 消除了所有不是n 的除数的数字(无论它们是否为素数)。因此,仅当in 的除数时才会执行其余代码。 Asymptotic bound for number of divisorsO(n^{1 / ln(ln(n))})

    最后,有一个函数check 遍历数组tempArr,其中包含到目前为止找到的n 的素数除数。一个正整数n 有多少个素数除数? Asymptotic bound for number of prime divisors 是最坏的情况(当n 被称为primorial numberO(ln(n) / ln(ln(n)))

    现在让我们总结一下。即使我们假设n 是原始的并且所有的主要除数都很快找到(所以array.length 有一个最大可能值),if(n%i) continue; 之后的代码部分的渐近复杂度是O(n^{1 / ln(ln(n))} * ln(n) / ln(ln(n)))。不是那么容易看到,但是它比O(sqrt(n)) 增长得慢,所以总复杂度是O(sqrt(n))

    【讨论】:

    • (sqrt(n) - 5) / 2 ,为什么要除以 2 ?
    • @J.Uchu 因为i += 2。您只检查 5 到 sqrt(n) 之间的奇数,即其中的一半。
    • 我的实际知识这么多数学,要学习数论,我应该知道什么?结石?矩阵? PS:我还在上学
    • @J.Uchu (质数)除数数的渐近界是高级数学,有许多涵盖该领域的科学论文。如果你还在上学,不要太在意它。先从研究big-o的更简单的算法开始,网上有很多例子。数论是一个单独的数学领域,如果您想深入研究,请从研究丢番图方程、同余、费马定理等开始。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-08-08
    • 1970-01-01
    • 1970-01-01
    • 2013-07-28
    相关资源
    最近更新 更多