首頁>Club>
5
回覆列表
  • 1 # 南極影解

    歷史背景

    Python的發明者曾參與ABC語言的開發,這種語言與當時主流的語言有較大的不同,它隱藏了較多底層的東西,力求使程式設計更簡單,它的語法也更接近自然語言,而非機器語言。這種做法的代價是程式的效率的降低,即完成同一件事,使用ABC語言對電腦效能的要求會更高。在當時,電腦的效能還相當有限,也並不太普及,多數使用者是具備一定相關知識的,他們大多用慣了之前的更高效的語言,不太願意犧牲效率去使用更平易近人的ABC(它在語法上與之前的語言有較大的不同,使用者還需要一定時間的學習)。ABC還有一個重要的問題:它不開源。這些因素使得ABC並沒有取得太大的成功。

    然而,它的確給了Guido一些啟發,為他後來開發Python提供了寶貴的經驗與教訓,Python繼承了ABC的一些特色,又彌補了它的很多不足,在可用性、可拓展性上有了較大的提升,加之後來計算機硬體飛速發展,犧牲一些效率來換取程式的簡單易寫、易維護是值得的。這類高階語言的出現使得程式設計師在寫程式時不用過多地糾結於底層細節,可以將更多的精力用於程式的設計上,不但促進了程式功能的豐富、提升,還使得程式設計得到了很好的普及,軟體的數量、質量的迅速上升,這些語言功不可沒。

    優點

    Python是一種簡潔、易上手、面向物件的語言,這使得使用者可以更清晰地進行程式設計,而不至陷入細節,且省去了很多重複工作。Python的底層以及很多庫是用C寫的,其執行速度相對較快(當然,比C、C++要慢一些)。Python是解釋型的語言,無需像C等語言一樣編譯後執行,這使得它的靈活性更強。

    Python是一種免費、開源的語言,這一點很重要,它對Python使用者群的擴大起到了至關重要的作用。而使用者的增加又豐富了Python的功能,使用者可以自由地釋出這個軟體的複製、閱讀它的原始碼、對它做改動、把它的一部分用於新的自由軟體中。這實際上是一種良性迴圈。

    Python擁有豐富的庫,並且可移植性非常強,可與C/C++等語言配合使用,使其能勝任很多的工作,如資料處理、圖形處理等。

    如今,Python已是一種知名度高、影響力大、應用廣泛的主流程式語言了,在電影製作、搜尋引擎開發、遊戲開發等等領域,Python幾乎都扮演了重要的角色。在未來的很長一段時間裡,Python很可能將有更強的功能、更大的使用者群,維持、鞏固它的重要地位。

  • 2 # 高利潔清洗裝置廠王總

    IT知識課堂

    歷史背景

    Python的發明者曾參與ABC語言的開發,這種語言與當時主流的語言有較大的不同,它隱藏了較多底層的東西,力求使程式設計更簡單,它的語法也更接近自然語言,而非機器語言。這種做法的代價是程式的效率的降低,即完成同一件事,使用ABC語言對電腦效能的要求會更高。在當時,電腦的效能還相當有限,也並不太普及,多數使用者是具備一定相關知識的,他們大多用慣了之前的更高效的語言,不太願意犧牲效率去使用更平易近人的ABC(它在語法上與之前的語言有較大的不同,使用者還需要一定時間的學習)。ABC還有一個重要的問題:它不開源。這些因素使得ABC並沒有取得太大的成功。

    然而,它的確給了Guido一些啟發,為他後來開發Python提供了寶貴的經驗與教訓,Python繼承了ABC的一些特色,又彌補了它的很多不足,在可用性、可拓展性上有了較大的提升,加之後來計算機硬體飛速發展,犧牲一些效率來換取程式的簡單易寫、易維護是值得的。這類高階語言的出現使得程式設計師在寫程式時不用過多地糾結於底層細節,可以將更多的精力用於程式的設計上,不但促進了程式功能的豐富、提升,還使得程式設計得到了很好的普及,軟體的數量、質量的迅速上升,這些語言功不可沒。

    優點

    Python是一種簡潔、易上手、面向物件的語言,這使得使用者可以更清晰地進行程式設計,而不至陷入細節,且省去了很多重複工作。Python的底層以及很多庫是用C寫的,其執行速度相對較快(當然,比C、C++要慢一些)。Python是解釋型的語言,無需像C等語言一樣編譯後執行,這使得它的靈活性更強。

    Python是一種免費、開源的語言,這一點很重要,它對Python使用者群的擴大起到了至關重要的作用。而使用者的增加又豐富了Python的功能,使用者可以自由地釋出這個軟體的複製、閱讀它的原始碼、對它做改動、把它的一部分用於新的自由軟體中。這實際上是一種良性迴圈。

    Python擁有豐富的庫,並且可移植性非常強,可與C/C++等語言配合使用,使其能勝任很多的工作,如資料處理、圖形處理等。

    如今,Python已是一種知名度高、影響力大、應用廣泛的主流程式語言了,在電影製作、搜尋引擎開發、遊戲開發等等領域,Python幾乎都扮演了重要的角色。在未來的很長一段時間裡,Python很可能將有更強的功能、更大的使用者群,維持、鞏固它的重要地位。

  • 3 # 使用者4243767351955

    本文出自《Python高手之路》中的Doug Hellmann訪談。

    我曾經有幸和Doug Hellmann一起工作過數月。他在DreamHost是一位非常資深的軟體開發工程師,同時他也是OpenStack專案的貢獻者。他發起過關於Python的網站Python Module of the Week(),也出版過一本很有名的Pyhton書The Python Standard Library By Example(),同時他也是Python的核心開發人員。我曾經諮詢過Doug關於標準庫以及庫的設計與應用等方面的問題。

    當你從頭開發一個Python應用時,如何邁出第一步呢?它和開發一個已有的應用程式有什麼不同?

    從抽象角度看步驟都差不多,但是細節上有所不同。相對於對比開發新專案和已有專案,我個人在對應用程式和庫開發的處理方式上有更多的不同。

    當我要修改已有程式碼時,特別是這些程式碼是其他人建立的時,起初我需要研究程式碼是如何工作的,我需要改進哪些程式碼。我可能會新增日誌或是輸出語句,或是用pdb,利用測試資料執行應用程式,以便我理解它是如何工作的。我經常會做一些修改並測試它們,並在每次提交程式碼前新增可能的自動化測試。

    建立一個新應用時,我會採取相同的逐步探索方法。我先建立一些程式碼,然後手動執行它們,在這個功能可以基本調通後,再編寫測試用例確保我已經覆蓋了所有的邊界情況。建立測試用例也可以讓程式碼重構更容易。

    這正是smiley()的情況。在開發正式應用程式前,我先嚐試用Python的trace API寫一些臨時指令碼。對於smiley我最初的設想包括一個儀表盤並從另一個執行的應用程式收集資料,另一部分用來接收透過網路傳送過來的資料並將其儲存。在新增幾個不同的報告功能的過程中,我意識到重放已收集的資料的過程和在一開始收集資料的過程基本是一樣的。於是我重構了一些類,並針對資料收集,資料庫訪問和報告生成器建立了基類。透過讓這些類遵循同樣的API使我可以很容易地建立資料收集應用的一個版本,它可以直接將資料寫入資料庫而無需透過網路傳送資料。

    當設計一個應用程式時,我會考慮使用者介面是如何工作的,但對於庫,我會專注於開發人員如何使用其API。透過先寫測試程式碼而不是庫程式碼,可以讓思考如何透過這個新庫開發應用程式變得更容易一點兒。我通常會以測試的方式建立一系列示例程式,然後依照其工作方式去構建這個庫。

    我還發現,在寫任何庫的程式碼之前先寫文件讓我可以全面考慮功能和流程的使用,而不需要提交任何實現的細節。它還讓我可以記錄對於設計我所做出的選擇,以便讀者不僅可以理解如何使用這個庫,還可以瞭解在建立它時我的期望是什麼。這就是我用在stevedore上的方法。

    我知道我想讓stevedore能夠提供一組類用來管理應用程式的外掛。在設計階段,我花了些時間思考我見過的使用外掛的通用模式,並且寫了幾頁粗略的文件描述這些類應該如何使用。我意識到,如果我在類的建構函式中放最複雜的引數,方法map()幾乎是可互換的。這些設計筆記直接寫進了stevedore官方文件的簡介裡,用來解釋在應用程式中使用外掛的不同模式和準則。

    將一個模組加入Python標準庫的流程是什麼?

    完整的流程和規範可以在Python Developer"s Guide()中找到。

    一個模組在被加入Python標準庫之前,需要被證明是穩定且廣泛使用的。模組需要提供的功能要麼是很難正確實現的,要麼是非常有用以至於許多開發人員已經建立了他們自己不同的變種。API應該非常清晰並且它的實現不能依賴任何標準庫之外的庫。

    提議一個新模組的第一步是在社群透過python-ideas郵件列表非正式地瞭解一下大家對此的感興趣程度。如果迴應很積極,下一步就是建立一個Python增強提案(PythonEnhancement Proposal,PEP),它包括新增這個模組的動因,以及如何過渡的一些實現細節。

    因為包的管理和發現工作已經非常穩定了,尤其是pip和Python Package Index(PyPI),因此在標準庫之外維護一個新的庫可能更實用。單獨的釋出使得對於新功能和bug修復(bugfix)的更新可以更頻繁,對於處理新技術或API的庫來說這尤其重要。

    標準庫中的哪三個模組是你最想人們深入瞭解並開始使用的?

    最近我做了許多關於應用程式中動態載入擴充套件方面的工作。我使用abc模組為那些作為抽象基類進行的擴充套件定義API,以幫助擴充套件的作者們瞭解API的哪些方法是必需的,哪些是可選的。抽象基類已經在其他一些語言中內建了,但我發現很多Python程式設計師並不知道Python也有。

    bisect模組中的二分查詢演算法是個很好的例子,一個廣泛使用但不容易正確實現的功能,因此它非常適合放到標準庫中。我特別喜歡它可以搜尋稀疏列表,且搜尋的值可能並不在其中。

    collections模組中有許多有用的資料結構並沒有得到廣泛使用。我喜歡用namedtuple來建立一些小的像類一樣的資料結構來儲存資料但並不需要任何關聯邏輯。如果之後需要新增邏輯的話,可以很容易將namedtuple轉換成一個普通的類,因為namedtuple支援透過名字訪問屬性。另一個有意思的資料結構是ChainMap,它可以生成良好的層級名稱空間。ChainMap能夠用來為模板解析建立上下文或者透過清晰的流程定義來管理不同來源的配置。

    許多專案(包括OpenStack)或者外部庫,會在標準庫之上封裝一層自己的抽象。例如,我特別想了解對於日期/時間的處理。對此你有什麼建議嗎?程式設計師應該堅持使用標準庫,還是應該寫他們自己的函式,切換到其他外部庫或是開始給Python提交補丁?

    所有這些都可以。我傾向於避免重複造輪子,所以我強烈主張貢獻補丁和改進那些能夠用來作為依賴的專案。但是,有時建立另外的抽象並單獨維護程式碼也是合理的,不管在應用程式內還是作為一個新的庫。

    你提到的例子中,OpenStack裡的timeutils模組就是對Python的datetime模組的一層很薄的封裝。大部分功能都簡短且簡單,但透過將這些最常見的操作封裝為一個模組,我們可以保證它們在OpenStack專案中以一致的方式進行處理。因為許多函式都是應用相關的,某種意義上它們強化了一些問題決策,例如,字串時間戳格式或者“現在”意味著什麼,它們不太適合作為Python標準庫的補丁或者作為一個通用庫釋出以及被其他專案採用。

    與之相反,我目前正致力於將OpenStack的API服務專案從早期建立時使用的WSGI框架轉成採用一個第三方Web開發框架。在Python中開發WSGI應用有很多選擇,並且當我們可能需要增強其中一個以便其可以完全適應OpenStack API伺服器的需要時,將這些可重用的修改貢獻對於維護一個“私有的”框架似乎更可取。

    當從標準庫或其他地方匯入並使用大量模組時,關於該做什麼你有什麼特別的建議嗎?

    我沒有什麼硬性限制,但是如果我有過多的匯入時,我會重新考慮這個模組的設計並考慮將其拆到一個包中。與上層模組或者應用程式模組相比,對底層模組的這種拆分可能會發生得更快,因為對於上層模組我期望將更多片段組織在一起。

    關於Python 3,有什麼模組是值得一提而且能令開發人員有興趣深入瞭解的?

    支援Python 3的第三方庫的數量已經到了決定性的時刻。針對Python 3開發新庫或應用程式從未如此簡單過,而且幸虧有3.3中加入的相容性功能使同時維護對Python 2.7的支援也很容易。主要的Linux發行版正在致力於將Python 3預設安裝。任何人要用Python建立新專案都應該認真考慮對Python 3的支援,除非有尚未移植的依賴。目前來說,不能執行在Python 3上的庫基本會被視為“不再維護”。

    許多開發人員將所有的程式碼都寫入到應用程式中,但有些情況下可能有必要將程式碼封裝成一個庫。關於設計、規劃、遷移等,做這些最好的方式是什麼?

    應用程式就是“膠水程式碼”的集合用來將庫組織在一起完成特定目的。起初設計時可以將這些功能實現為一個庫,然後在構建應用程式時確保庫的程式碼能夠很好地組織到邏輯單元中,這會讓測試變得更簡單。這還意味著應用程式的功能可以透過庫進行訪問,並且能夠被重新組合以構建其他應用程式。未能採用這種方法的話意味著應用程式的功能和使用者介面的繫結過於緊密,導致很難修改和重用。

    對於計劃開始構建自己的Python庫的人們有什麼樣的建議呢?

    我通常建議自頂向下設計庫和API,對每一層應用單一職責原則(Single Responsibility Principle,SRP)()這樣的設計準則。考慮呼叫者如何使用這個庫,並建立一個API去支援這些功能。考慮什麼值可以存在一個例項中被方法使用,以及每個方法每次都要傳入哪些值。最後,考慮實現以及是否底層的程式碼的組織應該不同於公共API。

    SQLAlchemy是應用這些原則的絕好例子。宣告式ORM、資料對映和表示式生成層都是單獨的。開發人員可以自行決定對於API訪問的正確的抽象程度,並基於他們的需求而不是被庫的設計強加的約束去使用這個庫。

    當你隨機看Python程式設計師的程式碼時遇到的最常見的程式設計錯誤是什麼?

    Python的習慣用法和其他語言的一個較大的不同在於迴圈和迭代。例如,我見過的最常見的反模式是使用for迴圈過濾一個列表並將元素加入到一個新的列表中,然後再在第二個迴圈中處理這個結果(可能將列表作為引數傳給一個函式)。我通常建議將過濾迴圈改成生成器表示式,因為生成器表示式,更有效也更容易理解。列表的組合也很常見,以便它們的內容可以以某種方式一起被處理,但卻沒有使用itertools.chain()。

    還有一些我在程式碼評審時給出的更細小的建議,例如,使用dict()而不是長的if:then:else塊作為查詢表,確保函式總是返回相同的型別(如一個空列表而不是None),透過使用元組和新類將相關的值合併到一個物件中從而減少函式的引數,以及在公共API中定義要使用的類而不是依賴於字典。

    有沒有關於選擇了一個“錯誤”的依賴的具體的例子是你親身經歷或目睹過的?

    最近,我有個例子,pyparsing()的一個新發布取消了對Python 2的支援,這給我正在維護的一個庫帶來了一點兒小麻煩。對pyparsing的更新是個重大的修改,而且是明確標識成這樣的,但是因為我沒有在對cliff()的設定中限制依賴版本號,所以pyparsing的新發布給cliff的使用者造成了問題。解決方案就是在cliff的依賴列表中對Python 2和Python 3提供不同的版本邊界。這種情況突顯了理解依賴管理和確保持續整合測試中適當的測試配置的重要性。

    你怎麼看待框架?

    框架像任何工具型別一樣。它們確實有幫助,但在選擇框架時要特別謹慎,應確保它能夠很好地完成當前的工作。

    透過抽取公共部分到一個框架中,你可以將你的開發精力專注於應用中獨特的方面。透過提供許多類似執行在開發模式或者寫一個測試套件這樣的引導程式碼,它們還可以幫你讓一個應用程式迅速達到一個可用的狀態而不是從頭開發。它們還可以激勵你在應用程式開發過程中保持一致,這意味著最終你的程式碼將更易於理解且更可重用。

    雖然使用框架時還有其他一些潛在的缺點需要注意。決定使用某個特定框架通常能夠反映應用程式本身的設計。如果設計的限制不能從根本上符合應用程式的需求,那麼選擇錯誤的框架會令應用的實現變得更難。如果你試著使用與框架建議不同的模式或慣用方式,你最終將不得不同框架做鬥爭。

  • 中秋節和大豐收的關聯?
  • 《海賊王》中的一刀流、二刀流、三刀流,哪一個流派比較適合戰鬥?