python數(shù)據(jù)結(jié)構(gòu)與算法--算法引入與時(shí)間復(fù)雜度

  • 算法引入:

    如果a+b+c=1000,且a2+b2=c^2(a,b,c為自然數(shù))去件,如何求出所有a,b扰路,c可能的組合尤溜?

    解決:枚舉法 思路:a=0,b=0汗唱,c=1/2/3....

    import time
    start_time = time.time()
    for a in range(0,1001):
      for b in range(0,1001):
          for c in range(0,1001):
              if a + b + c == 1000 and a**2 + b**2 == c**2:
                  print("a,b,c:%d,%d,%d"%(a,b,c))
    end_time = time.time()
    print("times:%ds"%(end_time-start_time))
    print("finished")
    輸出:
    a,b,c:0,500,500
    a,b,c:200,375,425
    a,b,c:375,200,425
    a,b,c:500,0,500
    times:261s
    finished
    
  • 算法是獨(dú)立存在的一種解決問題的方法與思想宫莱,對(duì)于算法而言,實(shí)現(xiàn)的語言并不重要哩罪,重要的是思想授霸。

  • 算法的五大特性

    • 輸入:算法具有0個(gè)或多個(gè)輸入
    • 輸出:算法至少有1個(gè)或多個(gè)輸出
    • 有窮性:算法在有限的步驟之后會(huì)自動(dòng)結(jié)束而不會(huì)無限循環(huán),并且每一個(gè)步驟可以在可接受的時(shí)間內(nèi)完成
    • 確定性:算法中的每一步都有確定的含義际插,不會(huì)出現(xiàn)二義性
    • 可行性:算法的每一步都是可行的碘耳,也就是說每一步都能夠執(zhí)行有限的次數(shù)完成

二、復(fù)雜度分析

1框弛、算法效率衡量

  • 上述例子算法改進(jìn):

    import time
    start_time = time.time()
    for a in range(0,1001):
      for b in range(0,1001):
          c = 1000 - a - b  #給出了a,b后,c的值就已經(jīng)是確定下來的了
          if a**2 + b**2 == c**2:
              print("a,b,c:%d,%d,%d"%(a,b,c))
    end_time = time.time()
    print("times:%ds"%(end_time-start_time))
    print("finished")
    輸出:
    a,b,c:0,500,500
    a,b,c:200,375,425
    a,b,c:375,200,425
    a,b,c:500,0,500
    times:2s
    finished
    
  • 執(zhí)行時(shí)間反應(yīng)算法效率

    由上述的兩段程序的執(zhí)行時(shí)間(261秒與2秒)辛辨,可以得出結(jié)論:實(shí)現(xiàn)算法程序的執(zhí)行時(shí)間可以反應(yīng)出算法的效率,即算法的優(yōu)劣。

  • 單靠時(shí)間值是不絕對(duì)可信的斗搞!

    假設(shè)第二次的算法實(shí)在一臺(tái)性能很差的計(jì)算機(jī)中運(yùn)行指攒,運(yùn)行時(shí)間可能與第一次運(yùn)行時(shí)間差不了多少,故:單純依靠運(yùn)行時(shí)間來比較算法的優(yōu)劣并不一定是客觀準(zhǔn)確的僻焚!程序的運(yùn)行離不開計(jì)算機(jī)環(huán)境(包括硬件和操作系統(tǒng))允悦,客觀原因影響程序運(yùn)行的速度,即每臺(tái)機(jī)器執(zhí)行的總時(shí)間不同虑啤,但是執(zhí)行的基本運(yùn)算數(shù)量大體相同隙弛,故下述引入時(shí)間復(fù)雜度概念。

2狞山、時(shí)間復(fù)雜度

(1)什么是大O驶鹉?

  • n表示數(shù)據(jù)規(guī)模,O(f(n))表示算法所需要執(zhí)行的指令數(shù)铣墨,和f(n)成正比。其中f(n)是n的一個(gè)函數(shù)办绝。
    在業(yè)界伊约,O(f(n))表示算法執(zhí)行的最低上界。(更詳細(xì)概念請(qǐng)百度)

    記T為執(zhí)行指令數(shù)

    上述第一個(gè)python代碼:T = 1000 * 1000 * 1000 * 2 (三個(gè)循環(huán)孕蝉,一條if語句屡律,一條print語句)

    若題目變?yōu)閍+b+c = 2000,則T = 2000 * 2000 * 2000 * 2

    改為a+b+c = n ,則T=n * n * n * 2

    總結(jié):對(duì)于一個(gè)算法來說降淮,T與數(shù)據(jù)規(guī)模n有關(guān)超埋,即T(n)= n^3*2,當(dāng)n較大時(shí)佳鳖,T(n)= n^3霍殴,常數(shù)不計(jì)。

    算法 所需執(zhí)行指令數(shù)
    二分查找法O(logn) a*logn
    尋找數(shù)組中的最大/最小值O(n) b*n
    歸并排序算法O(nlogn) c*nlogn
    選擇排序法O(n^2) d*n^2

    對(duì)于算法的時(shí)間性質(zhì)與空間性質(zhì)系吩,最重要的是其數(shù)量級(jí)和趨勢来庭,這些是分析算法效率的主要部分,而計(jì)量算法基本操作數(shù)量的規(guī)模函數(shù)中那些常量因子可以忽略不計(jì)穿挨。如上:a,b,c,d均為常數(shù) 月弛,當(dāng)數(shù)據(jù)規(guī)模較大時(shí),算法消耗的時(shí)間復(fù)雜度與這些常數(shù)關(guān)系不大科盛,而是與n所在項(xiàng)相關(guān)帽衙,故此時(shí)一般省略常數(shù)!

    例如:

    算法A:O(n) 所需執(zhí)行指令數(shù):10000*n

    算法B:O(n^2) 所需執(zhí)行指令數(shù):10*n^2

    對(duì)比不同n規(guī)模時(shí)算法A贞绵,B的指令數(shù)情況:

    n A的指令數(shù)10000n B的指令數(shù)10n^2 倍數(shù)
    10 10^5 10^3 100
    100 10^6 10^5 10
    1000 10^7 10^7 1
    10000 10^8 10^9 0.1
    10^5 10^9 10^11 0.01
    10^6 10^10 10^13 0.001

    可見厉萝,時(shí)間復(fù)雜度大O衡量的是量級(jí)的差異。當(dāng)n達(dá)到某個(gè)值時(shí),時(shí)間復(fù)雜度低的算法一定比時(shí)間復(fù)雜度高的算法運(yùn)算時(shí)間快冀泻,n越大常侣,差距越明顯。(數(shù)據(jù)規(guī)模較小時(shí)弹渔,時(shí)間復(fù)雜度高的算法有常數(shù)上的優(yōu)勢胳施,還是可以使用的,一般情況下肢专,使用復(fù)雜度較低的算法更優(yōu))

  • 若設(shè)計(jì)的算法有兩部分舞肆,則整個(gè)算法以量級(jí)最高的作為主導(dǎo)的時(shí)間復(fù)雜度。如:

    O(nlogn+n)= O(nlogn)

    O(nlogn+n^2)$= $O(n^2)

    注:上面式子的前提是 :這兩部分對(duì)應(yīng)的規(guī)模n是一樣的博杖,而像O(AlogA+B)這種類型的椿胯,此處A和B的規(guī)模可能不一樣剃根,故不能省略掉AlogA這部分(對(duì)鄰接表實(shí)現(xiàn)的圖進(jìn)行遍歷哩盲,時(shí)間復(fù)雜度是O(V+E),V是頂點(diǎn)數(shù)狈醉,E是邊數(shù)廉油,不能隨便替換)

(2)最壞時(shí)間復(fù)雜度

  • 分析算法時(shí),存在幾種可能的考慮:

    • 算法完成工作最少需要多少基本步驟苗傅,即最優(yōu)時(shí)間復(fù)雜度

    • 算法完成工作最多需要多少基本步驟抒线,即最壞時(shí)間復(fù)雜度

    • 算法完成工作平均需要多少基本步驟,即平均時(shí)間復(fù)雜度

    對(duì)于最優(yōu)時(shí)間復(fù)雜度渣慕,其參考價(jià)值不大嘶炭,反映的是最樂觀最理想的情況;對(duì)于最壞時(shí)間復(fù)雜度逊桦,提供了一種保證眨猎,表明算法在此種程度的基本操作中一定能完成工作;對(duì)于平均時(shí)間復(fù)雜度卫袒,全面反映算法的性質(zhì)宵呛,但其也會(huì)因?yàn)閼?yīng)用算法的實(shí)例分布不均勻而難以計(jì)算;因此夕凝,我們主要關(guān)注算法的最壞情況宝穗,即最壞時(shí)間復(fù)雜度

  • 算法復(fù)雜度在有些情況是用例相關(guān)(即與待排數(shù)據(jù)分布情況有關(guān))的,比如:

    插入排序算法O(n^2):最差情況:O(n^2)码秉;最好情況:O(n) 逮矛;平均情況(業(yè)界):O(n^2)

    快速排序算法O(nlogn):最差情況:O(n^2) (隨機(jī)化情況下,退化成最差情況的概率比較低)转砖;最好情況:O(nlogn)须鼎;平均情況(業(yè)界):O(nlogn)

(3)時(shí)間復(fù)雜度計(jì)算

  • 時(shí)間復(fù)雜度的幾條計(jì)算規(guī)則

    • 基本操作鲸伴,即只有常數(shù)項(xiàng),認(rèn)為其時(shí)間復(fù)雜度為O(1)
    • 順序結(jié)構(gòu)晋控,時(shí)間復(fù)雜度按加法計(jì)算
    • 循環(huán)結(jié)構(gòu)汞窗,時(shí)間復(fù)雜度按乘法計(jì)算
    • 分支結(jié)構(gòu),時(shí)間復(fù)雜度取最大值
    • 判斷一個(gè)算法的效率時(shí)赡译,往往只需關(guān)注操作數(shù)量的最高次項(xiàng)仲吏,其他次要項(xiàng)和常數(shù)項(xiàng)可以忽略
    • 在沒有特殊說明時(shí),我們所分析的算法的時(shí)間復(fù)雜度都是指最壞時(shí)間復(fù)雜度
  • 常見時(shí)間復(fù)雜度消耗時(shí)間大序蚍佟:
    O(1) < O(logn) < O(n) < O(nlogn) < O(n^2) < O(n^3) < O(n!) < O(2^n)

  • 問題:有一個(gè)字符串?dāng)?shù)組裹唆,將數(shù)組中每一個(gè)字符串按照字母序排序;之后再將整個(gè)字符串?dāng)?shù)組按照字典序排序只洒。整個(gè)操作的時(shí)間復(fù)雜度许帐?

    錯(cuò)誤解答:把字符串?dāng)?shù)組長度與每一個(gè)字符串的長度都統(tǒng)一當(dāng)成了n
    O(n*nlogn+nlogn)=O(n^2log2n)
    
    正確解答:
    --假設(shè)最長的字符串長度為s(因?yàn)榇驩算的是上界);數(shù)組中有n個(gè)字符串
    --對(duì)每個(gè)字符串排序:O(slogs)
    --將數(shù)組中的每一個(gè)字符串按照字母序排序:O(n*slogs)
    --將整個(gè)字符串?dāng)?shù)組按照字典序排序:O(s*nlog(n)) (排序算法中nlogn表示的是比較的次數(shù)毕谴,通常說的對(duì)整型數(shù)組排序只需進(jìn)行nlogn次比較成畦,是因?yàn)閮蓚€(gè)整數(shù)進(jìn)行比較在計(jì)算機(jī)中是O(1)級(jí)別的,而此處字符串比較字典序涝开,還需耗費(fèi)O(s)
    --綜上:O(n*slogs)+O(s*nlog(n))=O(n*slogs+s*nlog(n))=O(n*s*(logs+logn))
    
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末羡鸥,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子忠寻,更是在濱河造成了極大的恐慌,老刑警劉巖存和,帶你破解...
    沈念sama閱讀 206,378評(píng)論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件奕剃,死亡現(xiàn)場離奇詭異,居然都是意外死亡捐腿,警方通過查閱死者的電腦和手機(jī)纵朋,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,356評(píng)論 2 382
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來茄袖,“玉大人操软,你說我怎么就攤上這事∠芟椋” “怎么了聂薪?”我有些...
    開封第一講書人閱讀 152,702評(píng)論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長蝗羊。 經(jīng)常有香客問我藏澳,道長,這世上最難降的妖魔是什么耀找? 我笑而不...
    開封第一講書人閱讀 55,259評(píng)論 1 279
  • 正文 為了忘掉前任翔悠,我火速辦了婚禮,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘蓄愁。我一直安慰自己双炕,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,263評(píng)論 5 371
  • 文/花漫 我一把揭開白布撮抓。 她就那樣靜靜地躺著妇斤,像睡著了一般。 火紅的嫁衣襯著肌膚如雪胀滚。 梳的紋絲不亂的頭發(fā)上趟济,一...
    開封第一講書人閱讀 49,036評(píng)論 1 285
  • 那天,我揣著相機(jī)與錄音咽笼,去河邊找鬼顷编。 笑死,一個(gè)胖子當(dāng)著我的面吹牛剑刑,可吹牛的內(nèi)容都是我干的媳纬。 我是一名探鬼主播,決...
    沈念sama閱讀 38,349評(píng)論 3 400
  • 文/蒼蘭香墨 我猛地睜開眼施掏,長吁一口氣:“原來是場噩夢啊……” “哼钮惠!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起七芭,我...
    開封第一講書人閱讀 36,979評(píng)論 0 259
  • 序言:老撾萬榮一對(duì)情侶失蹤素挽,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后狸驳,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體预明,經(jīng)...
    沈念sama閱讀 43,469評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,938評(píng)論 2 323
  • 正文 我和宋清朗相戀三年耙箍,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了撰糠。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,059評(píng)論 1 333
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡辩昆,死狀恐怖阅酪,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情汁针,我是刑警寧澤术辐,帶...
    沈念sama閱讀 33,703評(píng)論 4 323
  • 正文 年R本政府宣布,位于F島的核電站施无,受9級(jí)特大地震影響术吗,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜帆精,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,257評(píng)論 3 307
  • 文/蒙蒙 一较屿、第九天 我趴在偏房一處隱蔽的房頂上張望隧魄。 院中可真熱鬧,春花似錦隘蝎、人聲如沸购啄。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,262評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽狮含。三九已至,卻和暖如春曼振,著一層夾襖步出監(jiān)牢的瞬間几迄,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評(píng)論 1 262
  • 我被黑心中介騙來泰國打工冰评, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留映胁,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 45,501評(píng)論 2 354
  • 正文 我出身青樓甲雅,卻偏偏與公主長得像解孙,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子抛人,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,792評(píng)論 2 345

推薦閱讀更多精彩內(nèi)容