14天阅读挑战赛

为了小杯子,一直在努力!


算法

  • 一、学习建议
  • 二、探讨算法
    • 算法具有以下特征
    • 优算法的判断标准
    • 时间复杂度
      • ① 常数阶
      • ② 线性阶
      • ③ 对数阶
      • ④ 平方阶
      • 最好、最坏、平均 的执行情况
    • 讲故事咯

这里我感觉《趣学算法》陈小玉教授 给的建议真的很不错。

一、学习建议

  1. 多角度,对比学习
    ①入门书籍,由简向复学习
    ②多本算法,对比学习
  2. 大视野,不求甚解
    ①优先级
    算法思路,解题思路>弄懂算法实现
    (不会因为某个公式/几行代码而“抛锚”停止不前)
  3. 多交流,见贤思齐
    “同学”,“教师”,“论坛”,“交流群”,“讲座”,“技术性活动”等
  4. 勤实践,越挫越勇
    不要一味的学习理论知识,“实践才是检验真理的唯一标准”,不惧怕失败,在错误中成长。
  5. 看电影,洞察未来
    科幻电影” 增长见识,有部分科幻电影中的情节,已经与我们见面了。

数据结构 +算法=程序

这句话我相信很多人都有所耳闻。包括我的老师也经常给我们灌输这一概念

二、探讨算法

  1. 算法具有以下特征

    ① 有穷性(不会出现无限循环,每个步骤在一个可以接受的时间内完成)
    ② 确定性(算法,每条语句都有确定的含义,不会出现二义性)
    ③ 可行性(每一步都能够通过执行有限次数完成)
    ④ 输入/输出(至少具备 0或n个输入 以及 1或n个输出)

  2. 优算法的判断标准

    ① 正确性( 可运行,无异常,可满足需求)
    ② 易读性( 方便阅读,理解、交流)
    ③ 健壮性( 对于“非法输入”,“异常” 等 , 对此有良好的反馈以及解决处理)
    ④ 高效性 (较少的时间,实现相同的需求)
    ⑤ 低存储性 (算法所需要的存储空间小,算法所占空间被称为“空间复杂度”)

  3. 时间复杂度

    不同的算法 ,所需 时间 以及 空间 不同。
    ② 同一种算法,在 不同的设备上,运行效率 不同。所以我们要比较算法的时候,建议在 同一设备 上进行对比测试。
    ③ 除此之外,算法还受 编写语言 的影响。(编译语言比解释语言快

    观看下面这一段代码

    #include <iostream>
    using namespace std;int test(int);int main()
    {cout<<"开始执行。。。"<<endl;       //执行一次 test(13);                        //进入test(int) 函数中。 cout<<"执行完毕"<<endl;            //执行一次 return 0;} int test(int n){for(int j = 1;j<=n;j++)     //注意将会执行n+1次,并非n次。 最后还会进行一次判断。 for(int i = 1;i<=n;i++)  //执行n(n+1) 次   cout<<"i:"<<i<<endl;    //执行n²次}
    

    上面例子中 : 共执行了 1+1+1+(n+1)+n(n+1)+n² = 2n²+2n+4次 ,使用函数T()表示
    T(n) = 2n²+2n+4

    测试:

     #include <iostream>using namespace std;// 2n²+2n+4double fun(int);// 2n²+2ndouble fun2(int);// 2n²double fun3(int);// n²double fun4(int);int main(){// n = 10;cout<<"当n=10: "<<endl<<"2(n^2)+2n+4精确值 --> " <<fun(10)<<endl<<"其中:2(n^2)+2n占-->"<<fun2(10)<<endl <<"其中:2(n^2)占 -->"<<fun3(10)<<endl<<"其中 n^2 占 -->"<<fun4(10)<<endl<<endl <<"比重情况:"<<endl<<"fun2(10):"<<fun2(10)/fun(10)<<endl<<"fun3(10):"<<fun3(10)/fun(10)<<endl<<"fun4(10):"<<fun4(10)/fun(10)<<endl<<endl<<endl; cout<<"================================"<<endl;    // n = 555;cout<<"当n=5555: "<<endl<<"2(n^2)+2n+4精确值 --> " <<fun(5555)<<endl<<"其中:2(n^2)+2n占-->"<<fun2(5555)<<endl <<"其中:2(n^2)占 -->"<<fun3(5555)<<endl<<"其中 n^2 占 -->"<<fun4(5555)<<endl<<endl <<"比重情况:"<<endl<<"fun2(5555):"<<fun2(5555)/fun(5555)<<endl<<"fun3(5555):"<<fun3(5555)/fun(5555)<<endl<<"fun4(5555):"<<fun4(5555)/fun(5555)<<endl<<endl<<endl; cout<<"================================"<<endl;    // n = 9999;   cout<<"当n=9999: "<<endl<<"2(n^2)+2n+4精确值 --> " <<fun(9999)<<endl<<"其中:2(n^2)+2n占-->"<<fun2(9999)<<endl <<"其中:2(n^2)占 -->"<<fun3(9999)<<endl<<"其中 n^2 占 -->"<<fun4(9999)<<endl<<endl <<"比重情况:"<<endl<<"fun2(9999):"<<fun2(9999)/fun(9999)<<endl<<"fun3(9999):"<<fun3(9999)/fun(9999)<<endl<<"fun4(9999):"<<fun4(9999)/fun(9999)<<endl<<endl<<endl; return 0;} /*方法实现*/double fun(int n){return 2*(n*n)+2*n+4;}double fun2(int n){return 2*(n*n)+2*n;} double fun3(int n){return 2*(n*n);}double fun4(int n){return n*n;}
    

    运行结果:

通过上面的例子,不难发现:n值越大,n²和2n²越贴近精确值。
最离谱的是,当n=9999时 , (1)2n²+2n 几乎等于 精确值 。(2)2n² 占比 0.9999。(3)其中 n²就占0.49995。所以在式子中 n² 的增长速度是最快的。
试想一下:当n=999999999999时 , n² 占 精确值 的多少呢?计算时间复杂度,我们不需要太多精准的值,我们的目的是在于比较两个算法的优异程度。

所以上面的式子中,我们可以写作为T(n) = n²

时间复杂度” 则记作 :T(n) = O(f(n))。 f(n) 是 式子 中n 的某个函数。 这就是“ 大O计法

使用“ 大O计法”表示则为 :O(n²)

① 常数阶

int main()
{int i = 4;                //执行一次 cout<<"i --> "<<i<<end;   //执行一次 int b = i +2;          //执行一次 cout<<"b --> "<<b<<end;   //执行一次return 0;
}

上方程序中,共执行了 f(n) = 1+1+1+1 = 4 次。
使用“大O记法”则为 : O(f(n)) = O(4) ❌ --> O(f(n)) = O(1) ✔
无论常数是几 , 我们都记作为1. 就算执行了 100 次。只要是常数阶 那么也记作为O(1)

② 线性阶

for(int i = 0;i<n;i++)     //代码体中执行了n次
{//代码体内容
}

那么f(n) = n , 所以其“时间复杂度”为 O(n)

③ 对数阶

int test(int n)
{int i = 1;while(i < n) //执行次数 = ?i *= 2;
}

变量 i 乘以 多少个2 , 大于n呢?
    可能是10个,也可能是10个 , 取决与n是多少。
    我们假设有x个 , 那么x = log2n
记作 :O(logn)

④ 平方阶

int test(int n)
{for(int i = 0;i<n;i++)   for(int j = 0;j<n;j++)//我是代码体                 //执行次数n*n次

其“时间复杂度”为 : O(n²)

后面我们还会介绍一种可怕的“时间复杂度

  1. 最好、最坏、平均 的执行情况

    什么? 这东西还分 最好,最坏,平均 的情况???
    其实也没这么复杂,其中有两种情况我们不管。
    吆西,我懂了,无论什么情况,我们都要做好最坏的打算,以方便应付意外的事情,是这样吗?
    你很聪明呀,我们继续往下看。

    给大家讲个例子:
     今天老师说调位置,恰好班级里面有一位长相极美的女生。
    最好的情况:她是我同桌。
    中肯的情况:我俩相隔的距离占总距离的 1/2。
    最坏的情况:我当上了 “舔狗”。

    带入到程序中:

    /**模拟strchr()
    */
    char * strchr(char* s,char i)
    {while(*s++ != '\0')if(*s == i) return s;return NULL;
    }
    

    如果我们运气好的话,第一次就找到了 变量 i,如果运气不好呢?那可能 i 在 s的结尾位置。中肯一点的话,i 在 s 的中间位置。

    除非有特殊说明,否则,我们按照 最坏的情况 进行计算。

讲故事咯

有这么一个故事,有一天国王与一个数学家下棋,他不相信这个数学家比他还聪明。
便对数学家,说:你如果赢了,我把国王送给你,但是如果你输了,你就要在全世界面前夸我比你聪明。
对局开始了,第一盘国王输了,国王对数学家说道:并没有规定一局定输赢。
一连下了好几盘,国王都输了,国王也是服气了。
这时,数学家说到:我不要你的国王 , 我只要米。
国王:米?你要多少
数学家:第一格放一粒米,第二格 放两粒米 ,后一格是上一格的两倍,一次类推。
国王看了看64格的棋盘,笑出了声。
结局我想大家都猜到了。
这个数学家就是 “阿基米德”。

对于上面的例子 1+2+2²+2³+…+263 这种属于爆炸式增长
对于上面的例子,我们可以变成
 S = 1+2+2²+2³+…+263
 2S = 2+2²+2³+…+264
 S = 2+2²+2³+…+264 - 1-2-2²-2³-…-263
  = 264 - 1
我们使用程序进行实现:

 第①方式:时间复杂度 O(n)

int main()
{double num = 1;           //执行一次for(int i = 1;i<=64;i++)   //执行n+1次num *= 2;             //O(1) 复杂度num--;                        //执行一次cout<<num<<endl;          //执行一次return 0;
}

这样我们很轻松的就算出了答案。

 第②方式:使用O(2n)复杂度进行计算。
如果对这个程序原理感兴趣可以dd我,这里我就不讲解了。

long test2(int n)
{static long num = 0;      //总和    static long index= 1;      //层数计算器,层数标识    int count = 1;             //因为是 (n=2)^n , 所以每次都只循环n=2次 while(count <= 2){num++;                   //总数+1 cout<<"num -->"<<num<<endl;      //方便监控 num 变量if(index!= n)         //如果不是最底层 {index++;           //层数标识+1 test2(n);         //递推开始 }count++;              //循环次数+1 } index--;                    //层数下移一层. return num/2;         // 2S = ...,所以需要除以2 , 求S
}


上面那个程序,我从写第一个字就开始执行了,到现在还没有执行完毕,可见其的可怕之处。
(也许国王的泪,如同这个程序一样,瀑布似得往下掉(滑稽保命!!!))
以后大家要避免这种算法。

会不会是你的程序有bug啊?
emm… 不排除这个可能,但我更希望你闭嘴


溜了溜了,我们下期见!

嘿,算法,哪里跑|你知道“时间复杂度”吗|算法初识相关推荐

  1. 一层循环时间复杂度_算法的时间与空间复杂度(一看就懂)

    算法(Algorithm)是指用来操作数据.解决程序问题的一组方法.对于同一个问题,使用不同的算法,也许最终得到的结果是一样的,但在过程中消耗的资源和时间却会有很大的区别. 那么我们应该如何去衡量不同 ...

  2. a*算法的时间复杂度_算法基础——时间复杂度amp;空间复杂度

    关注.星标公众号,学点计算机知识. 整理:persistenceBin 今天来跟大家继续分享一下数据结构的基础知识--算法效率的度量:时间复杂度和空间复杂度.首先来跟大家分享一下在电影<复仇者联 ...

  3. 算法的性能评价------空间复杂度和时间复杂度

    一个算法的优劣往往通过算法复杂度来衡量,算法复杂度包括时间复杂度和空间复杂度. 时间复杂度是算法的所需要消耗的时间,时间越短,算法越好.可以对算法的代码进行估计,而得到算法的时间复杂度. 一般来说,算 ...

  4. 排序算法的时间复杂度_算法的时间复杂度

    一. 算法的时间复杂度 1.如何评估算法的性能 数据结构和算法,本质上是解决现实存在的问题,即如何让解决指定问题的代码运行得更快?一个算法如果能在所要求的资源限制(resource constrain ...

  5. 【Java数据结构与算法】第六章 算法的时间复杂度、算法的空间复杂度和排序算法的介绍

    第六章 算法的时间复杂度.算法的空间复杂度和排序算法的介绍 文章目录 第六章 算法的时间复杂度.算法的空间复杂度和排序算法的介绍 一.算法的时间复杂度 1.时间频度 2.时间复杂度 3.常见的时间复杂 ...

  6. a*算法的时间复杂度_算法的时间复杂度:大O表示法

    本文讨论一下算法的时间复杂度问题,用到的素材取自<算法图解>一书,强烈推荐, 如有不妥,请联系我! 二分查找 随便想一个1-100的数字. 你的目标是以最少的次数猜到这个数字.你每次猜测后 ...

  7. python冒泡排序时间复杂度_Python算法中的时间复杂度问题

    在实现算法的时候,通常会从两方面考虑算法的复杂度,即时间复杂度和空间复杂度.顾名思义,时间复杂度用于度量算法的计算工作量,空间复杂度用于度量算法占用的内存空间. 本文将从时间复杂度的概念出发,结合实际 ...

  8. 【牛客网】:数据结构——时间复杂度,算法复杂度

    目录 一.时间复杂度 二.算法复杂度 一.时间复杂度  先看一张图: (1)时间频度 一个算法执行所耗费的时间,从理论上是不能算出来的,必须上机运行测试才能知道.但我们不可能也没有必要对每个算法都上机 ...

  9. python排序算法的时间复杂度_Python算法的时间复杂度和空间复杂度(实例解析)

    算法复杂度分为时间复杂度和空间复杂度. 其作用: 时间复杂度是指执行算法所需要的计算工作量: 而空间复杂度是指执行这个算法所需要的内存空间. (算法的复杂性体现在运行该算法时的计算机所需资源的多少上, ...

  10. 十分钟搞定时间复杂度(算法的时间复杂度)

    目录 一.什么是时间复杂度 二.时间复杂度的计算 单个循环体的推导法则 多重循环体的推导法则 多个时间复杂度的推导法则 条件语句的推导法则 习题练习 一.基础题 二.进阶题 三.再次进阶 一.什么是时 ...

最新文章

  1. python写一个通讯录step by step V3.0
  2. android AudioTrack 播放 正弦波 方波
  3. 谈谈我熟悉又陌生的cookie
  4. boost创建线程池_Java并发 之 线程池系列 (1) 让多线程不再坑爹的线程池
  5. CentOS学习笔记(一):中文语言包及输入法的安装使用
  6. 【spring cloud zookeeper】KeeperErrorCode = Unimplemented for
  7. linux的11186端口,linux – CentOS – semanage – 删除端口范围
  8. python程序的书写特点_不一样的Python代码写法,让你写出一手漂亮的代码
  9. SpringBoot入门 (一) HelloWorld
  10. 《机器学习实战》笔记(01):机器学习基础
  11. JSON.stringify(Data) 在IE8 里面不可用
  12. 单链表的插入删除以及逆转
  13. 【转】3个普通IO识别22个按键试验
  14. 走进Linq-Linq to SQL感性认识篇
  15. Rust : time,关于程序运行的计时
  16. 航模的无刷电机到底是什么电机
  17. 近来比较有意思的新形式网络广告
  18. JavaScript基础的全部东东
  19. larval 进程管理
  20. mac注销快捷键_mac关机的快捷键,不要强制关机。

热门文章

  1. unity鼠标固定在屏幕中间_unity3D技术之屏幕内跟随鼠标移动
  2. 前端制作PUBG瞄准镜!
  3. 投影向量=投影长度乘以单位向量
  4. Eclipse 照亮Java众生
  5. 起底Filecoin:易崩盘、估值高、政策风险大
  6. 图深度学习——复杂图嵌入:异质图,二分图,多维图,超图,符号图,动态图
  7. 2021最新Android常用开源库总结,建议收藏
  8. Facebook账号注册步骤
  9. Linux7 修改网卡名eth0
  10. linux提取声卡的codec教程,声卡Codec自动解析与ConfigData生成工具(Windows Version)