「第一門編程語言學C靠譜嗎?」git
「C還有將來嗎?」程序員
「我應該考慮學C嗎?」github
「C太老了吧!」數據庫
你是否也聽過相似的話語?編程
據說過無數次,有些是面對面的交談,而有些來自某個論壇。windows
雖然答案無非是「取決於具體狀況」,但以個人拙見,學習C編程是很是寶貴的經驗。安全
我想經過這篇短文向你展現C偉大的一面。服務器
首先,我想引用文檔C99RationaleV5.10中的一句話:網絡
C89委員會始終將保留C的傳統精神做爲主要目標。C的精神體如今不少方面,但其本質在於社區對C語言所依賴的基本原則的見解。C的精神能夠總結爲如下幾個方面:數據結構
● 相信程序員。
● 不阻礙程序員完成任務所需的工做。
● 保持語言短小精悍。
● 僅提供一種操做的方法。
● 保持高速,即便沒法保證可移植性。
下面,我將進一步討論上述幾點。
編程語言能夠大體分爲兩個級別:低級和高級。
低級語言靠近硬件,比低級語言更接近 CPU 的就只有電流了。這些語言又分爲爲機器碼和彙編兩種。前者是原始數據流,一般是二進制數據。爲了便於人類使用,一般咱們以「可讀」的十六進制形式進行處理。
第二代語言彙編在機器碼之上提供了一層抽象。這些語言大部分是人類可讀的符號(包括符號地址)、操做碼、地址、數字常量、字符串等的映射。並且每一個處理器各有不一樣。
相較而言,高級語言提供了哪些抽象?
根據維基百科:
與低級編程語言相比,高級語言使用了天然語言元素,更易於使用,並且還能夠自動化(甚至徹底隱藏)計算機系統中的重要領域(例如內存管理),從而簡化程序的開發過程,並且也比低級語言更易於理解。編程語言提供的抽象數量決定了其「高級」程度。
簡而言之:低級語言=更加靠近機器,高級語言=更加人性化。
C 是高級編程語言,但在 C 剛剛建立的時候,大多數功能仍然是經過低級的彙編完成的。所以,與其餘普遍使用的語言相比,C 擁有更底層的抽象級別,所以我喜歡將其稱爲「中級編程語言」。
你能夠輕鬆地將 C 代碼編譯成彙編(而不是二進制代碼),並檢查 CPU 執行的指令,在這個過程當中C語言不會加入太多語言特有的代碼。
此外,若是有須要,流行的 C 編譯器還提供了更低級的選項,容許你使用內聯彙編徹底掌控 CPU。縱觀編程領域,可以作到這一步的編程語言可謂少之又少。
低級語言的編程難度很高。不是由於這些語言過於複雜,而是由於這類編程很容易出錯,所以須要投入更多精力、記憶和心思。
C 是中級編程語言,所以「根據定義」 C 語言編程更加容易。但使人驚訝的是,與高級語言相比,C 語言的學習很是簡單。
爲何?
由於 C 語言的語法很是簡單,還有結構化的範例。循環、函數、結構、指針、變量、類型等核心基礎知識的學習都很是容易。大約只需一週的努力學習便可入門。剩下的就是數學和計算機科學理論了。
可是,不要誤會個人意思!若是想徹底掌握 C 語言,你須要付出大量的努力!事實上,學習任何東西都須要付出大量的努力!
與其餘語言(例如 Java )相比,標準 C 庫很小,因此你徹底能夠記住全部的功能。雖然有些功能應該在好久之前就棄用了,可是 C 語言的性能仍然很是出色。
若是連 libc 都以爲太大怎麼辦?即使你徹底不用 libc 也沒有關係。只要不包含括任何頭文件便可,甚至連簡單的 printf() 都不使用。你能夠將其替換成其餘庫。
C 語言很是成熟,重視對內存的管理,擁有內聯彙編、少許抽象,且語言沒有過分膨脹,所以程序員可以很好地控制程序。
所以,C 語言成爲了 OS 內核(Linux、Windows NT 或 macOS 的 XNU 等)以及其餘語言(例如 Python)的理想選擇。
這也是爲何 C 在嵌入式系統上如此受歡迎的緣由,由於嵌入式系統不容許浪費任何資源。
你可否想到任何沒有 C 編譯器的重大平臺?除了有些只運行彙編的平臺,我從未據說過沒有 C 編譯器的平臺。高端遊戲 PC、NASA 航天器、售票機等各類平臺都使用了 C 編程。真的是無所不在,C 軟件遍及全世界。
如上所述,對於圍繞在咱們平常生活中的微控制器和其餘形式的嵌入式系統來講,C 語言是主流選擇。
你據說過FFI嗎?事實證實,許多編程語言均可與 C 兼容。
你沒必要擔憂是否可在某些工做中使用 C 語言,99%的狀況下你均可以使用 C!(儘管這並不意味着你應該在全部工做中都使用 C……)。儘管 C 語言的代碼並不是100%可移植,但你能夠成爲可移植的程序員。
C 語言直接或間接地影響了無數語言,好比 C++、Java、Go、D、Rust、Perl,甚至是 PHP 和 Python。
顯然,學習這些語言的時候,你並不須要 C 的知識,有時甚至還不能使用C的最佳實踐。
然而,我認爲記住編程語言的根源很重要。並且,若是你熟悉 C,那麼就會有一些優點,尤爲是 C++ 的學習。
我懷疑以上對於 C 語言的快速、輕量級、中級編程語言、彙編等方面的討論,可能會給你一個錯誤的想法:你須要實現全部的功能。
雖然 C 確實沒有 Java中的 LinkedHashMap 或其餘功能(如垃圾收集器),但 C 語言也不至於那麼落後。
C 是一種成熟的流行語言。不管你須要何種功能,相信都能找到相應的庫(雖然有些功能太晦澀不容易表達,所以不太好找,但我相信這些庫必定存在)。
你須要垃圾收集器?那麼能夠試試 Boehm GC。你須要 TUI?那麼 ncurses是不二的選擇。還有不少不少庫,我沒法一一列舉:GTK、PDCurses、libcurl、ALSA、Genann、libsoundio、SDL、SQLite、getopt、OpenGL、inih、GMP、cJSON、MuPDF、OpenSSL...
C 是一種很是通用的語言,基本上能夠編寫任何東西:Web服務器、視頻遊戲(例如來自 id-Software 的經典遊戲,https://github.com/id-Software)、操做系統、其餘編程語言或強制 Firefox 遵照 XDG 基本目錄規範的包裝程序,由於若是我是管理員的話,這些程序會嚴格執行我下達的命令!
然而,請不要忘記,即使你能夠用 C 編寫全部軟件,也並不意味着你應該這樣作。例如,若是你想建立一個視頻遊戲,則應該將目光轉向 C++。
爲何我會在這裏引出 C++?由於 C++ 是當今使用最普遍的語言之一,並且相信你也常常遇到它。
與其餘兼容 C 的編程語言相反,C++ 是 C 的直接後代,並且 C++ 委員會不遺餘力保持與 C 的兼容性(達到複製粘貼便可使用的程度),在大多數狀況下,你能夠把 C 當成 C++ 同樣編譯。
但請不要誤會,C++ 絕對不是 C 的超集,C 代碼不能夠與 C++ 一塊兒使用,並且好的 C 代碼不必定是好的 C++ 代碼。舉個例子:
int* x = malloc(10 * sizeof(*x));
這在 C 語言中是正確的方法,可是在 C++ 中,malloc() 以前應該有 (int*),這樣才能正常工做,並且你應該使用 new int[10]。
儘管在大多數狀況下,你能夠在 C++ 項目中安全地使用 C 庫。
前面列舉的 C 庫不只可使用,並且人們常常以這種方式使用。例如,我本身在編寫十六進制編輯器Bym的時候就在 C++ 代碼中使用了 ncurses。
在 extern "C" 連接說明符的助力下,就連使用 C 編譯器編譯的庫也能夠與C++ 兼容。
C 語言是在B語言的基礎上於1972年建立的,所以多年來,C 吸取了一些古怪的東西(字符串標題中定義的 memcpy()!),有些功能已過期,有些已被棄用,C 保留了這些功能只是爲了與舊代碼兼容。
初學者極可能須要花費大量的時間來追查因爲內存損壞而引起的奇怪行爲,結果只弄得一頭霧水,極大地打擊程序員的信心。C 中幾乎沒有機制能夠阻止程序員搬起石頭砸本身的腳。
此外,咱們須要瞭解學習 C 不是計算機科學的入門。任何一門編程語言都不是計算機科學入門。你須要通過正規的學習才能對這片廣闊領域有真正的瞭解。即使沒法接受大學的正規教育,也能夠經過在線教育進行學習。
學習 C 是寶貴的經驗,很是值得。即使不做爲第一門語言,也應該做爲第2、第三或第四門編程語言進行學習。C 有不少優勢,但也有一些缺點。至少學習C 編程沒有任何損失。因此,請給本身一個機會,嘗試一下,也許你會愛上它。
最後,不要親信「 C 已經完了」、「很快 C 就會被淘汰了」之類的傳言。C 活得好好的,並且在接下來的幾十年中也將繼續發光發熱。別忘了,就連 COBOL 至今仍有空缺職位!
因此,C 怎麼可能會被淘汰?
最後,無論你是轉行也好,初學也罷,進階也可,若是你想學編程~
——【值得關注】個人 C/C++編程學習交流俱樂部!——
涉及:C語言、C++、windows編程、網絡編程、QT圖形界面開發、Linux編程、遊戲編程、數據結構與算以及數據庫......