1. <strong id="7actg"></strong>
    2. <table id="7actg"></table>

    3. <address id="7actg"></address>
      <address id="7actg"></address>
      1. <object id="7actg"><tt id="7actg"></tt></object>

        干貨 | 數(shù)據(jù)結(jié)構(gòu)與算法 - 什么是算法

        共 2796字,需瀏覽 6分鐘

         ·

        2020-02-12 23:21

        文案?向柯瑋
        排版 鄧發(fā)珩
        疫情尚未結(jié)束,今天繼續(xù)加油!在家好好學(xué)習(xí),好好充實(shí)自己,祝大家身體健康。

        229399287ffdab9402033d8da1d52006.webp

        前言


        大家好呀,? 我是小瑋~今天給大家?guī)?lái)的是學(xué)習(xí)筆記之?dāng)?shù)據(jù)結(jié)構(gòu)與算法--什么是算法。
        e60f3e0c9187126d75b991cf734d26d3.webp說(shuō)到算法呀,我相信每個(gè)學(xué)過(guò)編程的人都或多或少接觸到過(guò)。但是可能呢,你并不了解一個(gè)算法的定義是什么,算法好壞如何判斷,算法和數(shù)據(jù)結(jié)構(gòu)的關(guān)系,等等。讓我們帶著我們的疑問(wèn),慢慢地去走進(jìn)算法,去了解它。
        c7d1258fd9ed6de00f5b8293647005c1.webp
        本次學(xué)習(xí)筆記的主要內(nèi)容有:數(shù)據(jù)結(jié)構(gòu)和算法的關(guān)系,算法的定義,算法的特性,算法設(shè)計(jì)的要求,算法效率的度量方法,時(shí)間復(fù)雜度與空間復(fù)雜度。

        數(shù)據(jù)結(jié)構(gòu)與算法


        其實(shí)現(xiàn)在市面上關(guān)于數(shù)據(jù)結(jié)構(gòu)的書(shū)的名字,一般都不是單單以數(shù)據(jù)結(jié)構(gòu)為名,它通常是以數(shù)據(jù)結(jié)構(gòu)與算法為名,比如怎么學(xué)好數(shù)據(jù)結(jié)構(gòu)與算法。其實(shí)在算法導(dǎo)論中,也是把數(shù)據(jù)結(jié)構(gòu)和算法一塊講的。
        那么為什么他們總是在一塊呢?我們可以舉一個(gè)例子來(lái)說(shuō)。你把房子的基礎(chǔ)打好了,但是你沒(méi)有想好上面應(yīng)該怎么修,那房子還修不修?同理,你把上面怎么修想好了,基礎(chǔ)卻不知道怎么辦,那房子還修不修?
        再舉一個(gè)例子,你要去看話(huà)劇,發(fā)現(xiàn)話(huà)劇名字叫做《羅密歐》,很奇怪,就去問(wèn)前臺(tái)這是怎么回事,前臺(tái)解釋說(shuō),女主角生病了,演不了了,只有男主角了,所以這部話(huà)劇改為講男主角的心路歷程。那話(huà)劇還看得下去嗎?
        沒(méi)錯(cuò),數(shù)據(jù)結(jié)構(gòu)和算法的關(guān)系也是類(lèi)似,只學(xué)數(shù)據(jù)結(jié)構(gòu),你會(huì)感覺(jué)自己什么都沒(méi)有學(xué)到,只學(xué)算法,你會(huì)總感覺(jué)不能很完整。
        6ea12ee786a2e563f7ea9587e5ded944.webp

        算法的定義


        其實(shí)算法就是描述解決問(wèn)題的方法,它最早是花拉子米提出來(lái)的,沒(méi)錯(cuò)就是咱們數(shù)學(xué)書(shū)上面的花拉子米。從中可以看出,編程果然是與數(shù)學(xué)有著密不可分的關(guān)系啊。d2bf604b3fc61566a313fdcf885e7c5f.webp在現(xiàn)代,最普遍認(rèn)可的算法的定義是:算法是解決特定問(wèn)題求解步驟的描述,在計(jì)算機(jī)中表現(xiàn)為指令的有限序列,并且每條指令表示一個(gè)或多個(gè)操作。

        其實(shí)這個(gè)也很好理解,就是為了解決某個(gè)問(wèn)題,把一些指令按照順序排起來(lái),完成一些操作,這就是算法。

        算法的特性


        說(shuō)到算法的特征,一般來(lái)說(shuō)公認(rèn)的有五大基本特征,即:輸入,輸出,有窮性,確定性和可行性。

        輸入:這個(gè)其實(shí)相對(duì)來(lái)說(shuō)很容易理解,一個(gè)算法可以有零個(gè)或者多個(gè)輸入,比如說(shuō),我們第一次學(xué)編程的時(shí)候,我們做的第一個(gè)算法是什么?沒(méi)錯(cuò),就是輸出‘hello world’,這個(gè)就不需要咱們輸入?yún)?shù),但是絕大多數(shù)算法都是需要我們輸入一些參數(shù)進(jìn)去的。
        輸出:一個(gè)算法最起碼會(huì)有一個(gè)或者多個(gè)輸出,如果你的算法沒(méi)有輸出,你設(shè)計(jì)它干什么呢?
        有窮性:它在嚴(yán)格意義上來(lái)講,并不僅僅是數(shù)學(xué)意義上無(wú)窮的對(duì)立,它是指程序在人們可以接受的時(shí)間范圍內(nèi)完成,如果一個(gè)程序陷入了無(wú)限循環(huán),或者一個(gè)算法需要運(yùn)算幾十年,那都算無(wú)窮,那都是沒(méi)有意義的算法。
        確定性:這個(gè)也非常容易理解,算法的每一個(gè)步驟都具有確定的意義,不會(huì)出現(xiàn)多重含義,算法在一定的條件下,只能有一條執(zhí)行路徑。一旦出現(xiàn)了歧義,那么編譯器就會(huì)報(bào)錯(cuò),我相信這一點(diǎn)大家都理解吧?
        可行性:算法的每一步都必須是可執(zhí)行的,也就是說(shuō),每一步都能夠通過(guò)執(zhí)行有限次數(shù)完成。這一點(diǎn),我感覺(jué)有有窮性有異曲同工之處。

        算法設(shè)計(jì)的要求


        我們都知道,想要實(shí)現(xiàn)某種目的,我們可以設(shè)計(jì)多種多樣的算法去實(shí)現(xiàn),但是一個(gè)好的算法,他一般都滿(mǎn)足以下的特點(diǎn)。

        正確性:它的意思是,算法至少應(yīng)該具有輸入,輸出和加工處理無(wú)歧義,能正確反映問(wèn)題的需求,能夠得到問(wèn)題的正確答案。它主要包括四個(gè)層次:1、沒(méi)有語(yǔ)法錯(cuò)誤。2、對(duì)于合法的輸入,能夠給出滿(mǎn)足要求的輸出。3、對(duì)于錯(cuò)誤的輸入,能夠給出相應(yīng)規(guī)格提示的輸出。4、對(duì)于各種刁難的輸入,也能給出滿(mǎn)足要求的輸出。
        可讀性:它的意思是,算法設(shè)計(jì)的另一目的是為了便于閱讀,理解和交流。對(duì)于一個(gè)優(yōu)秀的算法而言,它不僅僅要求是解決這個(gè)問(wèn)題,它還要求別人能夠理解,這樣也有利于算法問(wèn)題的發(fā)現(xiàn)以及改進(jìn),同時(shí)更是方便自己以后回來(lái)再看的時(shí)候能夠明白。
        在這里我想到了一個(gè)例子,前段時(shí)間有很多有用最少代碼完成xxx的挑戰(zhàn),很多大神確實(shí)用了很少很少的代碼,完成了這些挑戰(zhàn),但是代碼最終公布出來(lái),很少人能夠明白其中的意思,這樣的代碼就不屬于好的代碼。

        健壯性:它的意思是,能夠?qū)﹀e(cuò)誤的數(shù)據(jù)進(jìn)行正確的相應(yīng)處理,而不是輸出一些稀奇古怪的東西。舉個(gè)例子來(lái)說(shuō),你設(shè)計(jì)了一款根據(jù)路程求時(shí)間的算法,他們輸入了一個(gè)負(fù)數(shù)進(jìn)來(lái),你的算法應(yīng)該能夠給出相應(yīng)的回復(fù),而不是異常的回復(fù)。
        時(shí)間效率高并且儲(chǔ)存量低:這個(gè)其實(shí)就是評(píng)判算法好壞最關(guān)鍵的一點(diǎn),也是從事優(yōu)化算法行業(yè)的人最高的追求。就和人們?cè)诂F(xiàn)實(shí)生活中一樣,我們總是想用最少的投入,獲得最大的收益。那么一款優(yōu)質(zhì)的算法也是一樣,它講究用最快的時(shí)間,最少的空間,去完成最多的任務(wù)。
        1065ac2f3ba84dc8268aba386522a175.webp

        算法效率的度量方法


        對(duì)于一個(gè)算法的效率,我們應(yīng)該怎么度量呢?它主要分為兩種:事后統(tǒng)計(jì)方法和事前分析估算方法。

        事后統(tǒng)計(jì)方法:這種方法主要是通過(guò)設(shè)計(jì)好程序以后的測(cè)試程序和數(shù)據(jù),利用計(jì)算器對(duì)不同算法編制的程序的運(yùn)行時(shí)間進(jìn)行比較,從而判斷算法的效率。這種方法的缺陷很明顯。我覺(jué)得主要有以下幾點(diǎn):
        >有可能導(dǎo)致花費(fèi)了大量時(shí)間去寫(xiě)一個(gè)程序,最后運(yùn)行了發(fā)現(xiàn)是一個(gè)很糟心的程序 。


        >比較的方式有誤,運(yùn)行時(shí)間不僅僅是取決于算法的好壞,同時(shí)也取決于電腦配置的好壞,你用同樣的算法在最先一代電腦上運(yùn)行和在現(xiàn)在最旗艦的電腦上運(yùn)行,效果肯定存在巨大差異。


        >測(cè)試數(shù)據(jù)存在選擇問(wèn)題,你不知道自己的算法應(yīng)該選取多大的數(shù)據(jù),就那排序算法來(lái)說(shuō),幾個(gè)數(shù)字的排序,無(wú)論哪一種算法,其實(shí)都差不多,只有當(dāng)數(shù)據(jù)非常大的時(shí)候才會(huì)有明顯差異。


        b83ecff2f34f627b805e1d9e7d0ec9ec.webp
        事前估算分析方法:它的意思是,在編譯之前,就依據(jù)統(tǒng)計(jì)方法對(duì)算法進(jìn)行估算。那么這個(gè)估算主要是在哪些方面呢?

        >算法采用的策略,方法。


        >編譯產(chǎn)生的代碼質(zhì)量。


        >問(wèn)題的輸入規(guī)模。


        >機(jī)器執(zhí)行指令的速度。


        第一條當(dāng)然是算法好壞的根本,第二條是由編譯器決定的,第四條需要看電腦的性能,也就是說(shuō),不考慮軟件和硬件,一個(gè)程序的運(yùn)行時(shí)間其實(shí)是取決于算法的好壞和問(wèn)題的輸入規(guī)模(即輸入量的多少)。
        下面我們舉一個(gè)例子來(lái)說(shuō)明一下。等差數(shù)列求和,大家肯定都知道吧?那么針對(duì)這個(gè)問(wèn)題,我們可以設(shè)計(jì)兩種最常規(guī)的算法。
        1:cin>>n;int?i,sum=0;for(i=1;i<=n;i++)sum+=i;cout<2:cin>>n;int?sum=0;sum=(1+n)*n/2cout<

        在這兩種算法中,雖然我們輸入的是一樣的,但是內(nèi)部的計(jì)算過(guò)程是完全不在一個(gè)等級(jí)的,這就是1與n的差距。對(duì)吧?

        我們?cè)诜治龀绦驎r(shí)間的時(shí)候,就應(yīng)該把程序當(dāng)成是獨(dú)立于程序語(yǔ)言一系列步驟,我們把其中的基本操作的數(shù)量和輸入規(guī)模聯(lián)系起來(lái)。

        就拿上面的例子來(lái)說(shuō),對(duì)于同樣的輸入規(guī)模n,方法一需要運(yùn)n^2次,而方法二只需要運(yùn)行n次。這就是一個(gè)質(zhì)的飛躍。

        302a5e6b744e5141ca9682fa18c2c662.webp

        時(shí)間復(fù)雜度與空間復(fù)雜度


        說(shuō)到這兩個(gè)概念,雖然在書(shū)上看到很多相關(guān)的內(nèi)容但是我覺(jué)得我們只需要關(guān)注兩個(gè)方面,即:它們的意思是什么,它們?cè)趺赐茖?dǎo)。

        時(shí)間復(fù)雜度:我們通常用O(x)來(lái)表示時(shí)間復(fù)雜度,它的意思是在最壞的條件下,這個(gè)程序會(huì)運(yùn)行多少次。打個(gè)比方來(lái)說(shuō),我們現(xiàn)在用冒泡排序?qū)γ嫦旅娴臄?shù)組進(jìn)行排序。1046d598c7265e59c2bab90d994e9889.webp我們只需要運(yùn)行一次就可以完成我們的目的,但是如果是下面這個(gè)數(shù)組呢?
        365ca1122dd710e5960e80aa380edc6f.webp是不是相應(yīng)的,程序運(yùn)行次數(shù)就更復(fù)雜了?那么最壞的情況是什么樣的呢?b5ddee16b479f5ff5f8a2201de3d5795.webp沒(méi)錯(cuò),就是這種情況,那么這種情況下,程序會(huì)運(yùn)行多少次?是8^2=64次吧?那么依據(jù)我們的定義,冒泡排序的時(shí)間復(fù)雜度就是O(n^2)。
        我們通常將推導(dǎo)時(shí)間復(fù)雜度的過(guò)程叫做,推導(dǎo)大O階,那么就可以知道,我們把上面出現(xiàn)的n^2,稱(chēng)為平方階,把n稱(chēng)為線(xiàn)性階,那么,現(xiàn)在我們來(lái)思考一下,如果是lg(n)呢?沒(méi)錯(cuò),就是對(duì)數(shù)階了。
        在推導(dǎo)的過(guò)程當(dāng)中,我們應(yīng)該注意的是:


        >如果這個(gè)n為一個(gè)常數(shù),我們統(tǒng)一認(rèn)為時(shí)間復(fù)雜度是O(1)。


        >如果n的前面存在系數(shù),我們統(tǒng)一認(rèn)為時(shí)間復(fù)雜度是O(n),即把前面的系數(shù)當(dāng)成1處理。


        >如果最終算出時(shí)間復(fù)雜度為O(n^2+n-i)的類(lèi)似形式,我們只保留最高階。



        空間復(fù)雜度 :既然已經(jīng)有了時(shí)間復(fù)雜度的基礎(chǔ),那么空間復(fù)雜度也就不難理解了。而且如果出現(xiàn)了復(fù)雜度,在通常情況下,都是指的時(shí)間復(fù)雜度。
        我在這里就不多加介紹空間復(fù)雜度了。我們直接寫(xiě)出空間復(fù)雜度的表示方法。S(n)=O(f(n)),這里n是問(wèn)題的規(guī)模,f(n)是關(guān)于n所占儲(chǔ)存空間的函數(shù)。

        到這個(gè)位置為止,我們基本上已經(jīng)完全了解了數(shù)據(jù)結(jié)構(gòu)和算法的一些基本內(nèi)容。在之后的推文中,我們就正式進(jìn)入數(shù)據(jù)結(jié)構(gòu)與算法的主體內(nèi)容了。
        49aed12a00d2321f5a2580f3e25f4396.webp
        希望各位看客老爺能夠認(rèn)真地讀好前兩篇推文,這是一個(gè)非常重要的基礎(chǔ)部分。那么,我們下期再見(jiàn)啦~
        cf6707902514b77077dc5c4cf0adb231.webp

        瀏覽 63
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        評(píng)論
        圖片
        表情
        推薦
        點(diǎn)贊
        評(píng)論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        1. <strong id="7actg"></strong>
        2. <table id="7actg"></table>

        3. <address id="7actg"></address>
          <address id="7actg"></address>
          1. <object id="7actg"><tt id="7actg"></tt></object>
            国产精品爱久久久久久久威尼斯 | 国产免费人做人爱午夜视频 | 国产麻豆电影 | 校园淫事校长h倪校长 | 久久影院三极片 | 国产精品秘 精品久久久 | 成人免费视频 视频免费看 | 国产一页| 亚洲一区二区三区乱字幕高清红楼 | 成人性生交大片免费影视无遮挡 |