在刷LeetCode-1TwoSum的时候,有个人在论坛留言,大致意思如下:

  1. 我的算法击败了90%的人,O(nlgn)算法比O(n)算法快。

我觉得这个人是不懂算法的。让我一步一步解释。

# O的含义

通俗的说,O表示忽略系数的复杂度上限,常常用一个量级表示,比如n,nlgn。

# 忽略的系数重要吗

重要。我觉得《算法》比《算法导论》优秀的原因之一是,作者用实例证明,在不少情况下,复杂度之前的系数很重要。比如,系数可以导致O(n^2)的插入排序可以比O(nlgn)快速排序快。

可以看一个例子。

  1. // 伪代码,程序1
  2. void add(int num)
  3. {
  4. num++;
  5. num++;
  6. num++;
  7. num++;
  8. num++;
  9. num++;
  10. num++;
  11. num++;
  12. num++;
  13. num++;
  14. }
  15.  
  16. void add(int[] nums)
  17. {
  18. for (int i = ; i < n; i++)
  19. add(nums[i]);
  20. }
  1. // 伪代码,程序2
  2. void add(int num)
  3. {
  4. num++;
  5. }
  6.  
  7. void add(int[] nums)
  8. {
  9. for (int i = ; i < n; i++)
  10. for (int j = ; j < n; j++)
  11. add(nums[i]);
  12. }

程序1的时间复杂度为O(n),程序2的时间复杂度为O(n^2)。如果从O来看,程序2的执行速度一定会比程序1快。

实际上速度相当。假设nums的大小为10,程序1要执行10 * 10 = 100次i++,程序2同样执行10 * 10 * 1 = 100次i++。

原因就在于,程序1需要的时间是10 * n,系数很大为10,而程序2需要的时间是1 * n ^ 2,系数很小为1。

# 那个人错在哪里

或许不是他的错,是LeetCode的错。

渐进时间一定要在系数相对于数据量比重很小很小的时候,才有用。像排序算法一类比较简单的算法,需要上十万的数据量,才能体现出复杂度为nlgn和n^2的细小区别。

这个人用了很聪明很简单的算法,没有用复杂的数据结构,全是基本变量,时间复杂度为O(nlgn)。而O(n)用了Hashtable,共有n个数,对于每个数,Hashtable里面有很多计算的过程,系数很大。

此题,LeetCode可能单个数据集不是很大,系数显得格外重要。

# 链接

Q: https://leetcode.com/problems/two-sum/

A: https://github.com/mofadeyunduo/LeetCode/tree/master/1TwoSum

(请多多支持我刚刚建立的GitHub和博客,谢谢,有问题可以邮件609092186@qq.com或者留言,我尽快回复)

我们为什么不能只用O记号来谈论算法?的更多相关文章

  1. 用大O记号法测量算法的效率(Algorithm efficiency Asymptotic notation Big O notation)

    为什么要了解算法的效率? 一般来说,编程就是把各种已知的算法代入到自己的代码当中,以此来解决问题.因此,了解各种算法的效率对于我们选择一个合适的算法有很大帮助. 算法的效率由什么确定? 从算法分析的理 ...

  2. 当我们谈论算法我们在谈论什么:由疫情核酸检测想到的分治算法(Divide-and-Conquer)

    原文转载自「刘悦的技术博客」https://v3u.cn/a_id_159 北京的疫情一波未平一波又起,由此看来,战"疫"将是一场旷日持久的战争,绝不能掉以轻心.轻易言胜.病毒随时 ...

  3. JVM 平台上的各种语言的开发指南

    JVM 平台上的各种语言的开发指南 为什么我们需要如此多的JVM语言? 在2013年你可以有50中JVM语言的选择来用于你的下一个项目.尽管你可以说出一大打的名字,你会准备为你的下一个项目选择一种新的 ...

  4. 用 C# 读取二进制文件

    当想到所有文件都转换为 XML时,确实是一件好事.但是,这并非事实.仍旧还有大量的文件格式不是XML,甚至也不是ASCII.二进制文件仍然在网络中传播,储存在磁盘上,在应用程序之间传递.相比之下,在处 ...

  5. Analysis of Algorithms

    算法分析 Introduction 有各种原因要求我们分析算法,像预测算法性能,比较不同算法优劣等,其中很实际的一条原因是为了避免性能错误,要对自己算法的性能有个概念. 科学方法(scientific ...

  6. CSS3全览_动画+滤镜

    CSS3全览_动画+滤镜 目录 CSS3全览_动画+滤镜 1. 列表和生成的内容 2. 变形 3. 过渡 4. 动画 5. 滤镜, 混合, 裁剪和遮罩 6. 针对特定媒体的样式 作者: https:/ ...

  7. NHibernate系列文章二:创建NHibernate工程

    摘要 这篇文章介绍了如何创建一个简单的使用NHibernate的控制台应用程序,包括使用NuGet.简单的配置.单表映射.对NHibernate配置文件添加智能提示.使用ISessionFactory ...

  8. [ay原创作品]用wpf写了个模仿36Kr网站登录背景的效果

    这里我借鉴了,上周比较火的一个前端文章,人家用js去写的,地址 自己用wpf也写了一个,但是它的  粒子比较,然后连线算法真的很差,他创建了一个加入鼠标点的集合,2个集合进行比较,并且粒子会向鼠标靠近 ...

  9. 学习理论之正则化(Regularization)与模型选择

    一.引言 对于一个学习问题,可以假设很多不同的模型,我们要做的是根据某一标准选出最好的模型.例如,在多项式回归中,对于我们的假设模型,我们最要紧的是决定 k 到底取多少合适,能不能有一种方法可以自动选 ...

随机推荐

  1. ADO.NET对象的详解

    1. Connection 类 和数据库交互,必须连接它.连接帮助指明数据库服务器.数据库名字.用户名.密码,和连接数据库所需要的其它参数.Connection对象会被Command对象使用,这样就能 ...

  2. iOS可视化动态绘制八种排序过程

    前面几篇博客都是关于排序的,在之前陆陆续续发布的博客中,我们先后介绍了冒泡排序.选择排序.插入排序.希尔排序.堆排序.归并排序以及快速排序.俗话说的好,做事儿要善始善终,本篇博客就算是对之前那几篇博客 ...

  3. ElasticSearch 5学习(10)——结构化查询(包括新特性)

    之前我们所有的查询都属于命令行查询,但是不利于复杂的查询,而且一般在项目开发中不使用命令行查询方式,只有在调试测试时使用简单命令行查询,但是,如果想要善用搜索,我们必须使用请求体查询(request ...

  4. HTML5新特性有哪些,你都知道吗

    一.画布(Canvas) 画布是网页中的一块区域,可所以用JavaScript在上面绘图.下面我们来创建一个画布并在上面绘制一个坦克(后面将用HTML5做一个坦克大战游戏),代码如下: <!DO ...

  5. JAVA问题集锦Ⅰ

    1.Java的日期添加: import java.util.Date ; date=new date();//取时间 Calendar calendar = new GregorianCalendar ...

  6. Yeoman 官网教学案例:使用 Yeoman 构建 WebApp

    STEP 1:设置开发环境 与yeoman的所有交互都是通过命令行.Mac系统使用terminal.app,Linux系统使用shell,windows系统可以使用cmder/PowerShell/c ...

  7. jquery屏幕滚动计算事件总结

    获取浏览器显示区域(可视区域)的高度 : $(window).height(); 获取浏览器显示区域(可视区域)的宽度 : $(window).width(); 获取页面的文档高度: $(docume ...

  8. web 前端(轮番插件)

    <!DOCTYPE html> <html lang="zh-cn"> <head> <meta charset="UTF-8& ...

  9. Linux命令【第三篇】

    执行下面命令时发现提示需要输入密码,请问提示输入的密码是哪个用户的密码. [test@oldboy ~]$ sudo su - oldboy 解答: 输入当前执行命令test账户的密码. 相关说明: ...

  10. TCP/IP之Nagle算法与40ms延迟

    Nagle算法是针对网络上存在的微小分组可能会在广域网上造成拥塞而设计的.该算法要求一个TCP连接上最多只能有一个未被确认的未完成的小分组,在该分组确认到达之前不能发送其他的小分组.同时,TCP收集这 ...