關於C語言 我喜歡和討厭的十件事
最近有個傢伙抱怨道“為什麼我還要再用C?”-雖然我不同意他的說法,但至少他隨口提到如果你“在一臺拇指大小的電腦”上程式設計,或者為一門語言寫載入程式,那麼可以用C語言。要我說,寫裝置驅動,或者特定平臺的核心,不管怎麼說都可以使用C。
幾年之前,我用C語言寫下了我的第一個網路程式,但我並不推薦這麼做。現在,我只用P打頭的,尤其是P-y打頭的語言寫網路程式(譯者注:繞什麼圈子,不就是Python嘛…)。但在當時,我剛從DOS和TSRs的世界中出來,在那兒用上10KB的RAM我都會覺得大得驚人。
現在我是一名Web開發者,但是僅限於晚上。白天我為嵌入式微處理器編寫韌體,因此,C依舊是我所選擇的語言。我所說的微處理器是那種嵌入烤麵包機,或者其他類似裝置中的處理器,只有大概64KB的程式碼空間以及2KB的RAM。因此,可供選擇的語言基本上就只有彙編和C了。(也可以是Forth,不過那是另外的故事。)
然後,我漸漸發現越是多用C,就越不覺得它討厭了。因此我就想著要給這個世界最常用的系統級程式語言寫一些頌詞。
以下分別是關於C語言我喜歡五件事和討厭的五件事。請隨意在底下的評論欄里加上你們自己喜歡或討厭的事情。
1.K&R(喜歡)
Kernighan & Ritchie 寫的《C程式設計語言》是關於C語言最好的書,而且我估計它也是關於程式設計的最好的書之一。簡潔明瞭,都是有用並且重要的例子。這是一本非常好的書,同時也是一個非常好的參考。
甚至就連序言都非常好。在此引用一句,“C不是一門龐大的語言,因此不應該用一本厚重的書來詮釋。”如果所有的程式設計教程都像這本書一樣把長度限制到270頁,它們會好很多。K&R的簡潔明瞭、點到為止,很可能是C語言的成功所不可或缺的。
另一本給我喜愛的類似的程式設計教材是Leo Brodie所著的《Thinking Forth》。當然,肯定還有其他非常好的書,像是SICP之類的,只是我還沒有讀過罷了。
2.它十分簡明(喜歡)
事實上,C語言作為一門簡明語言是一個實實在在的福利。想要學習C,你只需瞭解它的型別,熟悉流程控制,處理好指標,然後你基本上就已經掌握它了。剩下的就僅僅是函式了。事實上,K&R利用這個低階的命令式語言,僅花費11行就實現了qsort(),不得不說這是對C語言簡明性有力的證明。
3.IOCCC(喜歡)
你或許會覺得我瘋了,不過如果你足夠上進,International Obfuscated C Code Contest可能那兒是關於電腦科學最好的老師之一。算我開的一個小玩笑,不過我的確認為眾多黑客都在不停挑戰,並且創造了很多值得一談的功績。
其中讓我確實學到很多的就是OTCC,Fabrice Bellard所寫的“混淆的小型C編譯器”。從中我學到了關於編譯器設計的知識,主要是C語言編譯器不必是340萬行程式碼的龐然大物。同時,我也從Let’s Build a Compiler中獲益,並靜下來寫了一個迷你的由C到Forth的編譯器。
4.變數的定義與使用形式相似(喜歡)
這一點對記住如何定義十分複雜的事物非常有用,舉個例子,一個指向包含十個整形的陣列的指標應該是int *api[10]還是int (*pai)[10]呢?像你使用它的方式一樣定義它即可,只需要記住[]操作符的優先順序高於*(很自然就可以記住),然後你就明白那個括號是需要的了。(譯者注:前者是指標陣列,包含十個指向整形的指標。)
5.它編譯出的“hello, world”體積很小(喜歡)
尤其是對嵌入式程式設計,這一點簡直棒極了。C語言之上沒有一個體積龐大的執行時,在很多嵌入式處理器上,一個什麼都不做的程式一般只會編譯出3到4個byte。一個完整的“hello, world”程式,甚至是在Windows XP下,都只會編譯出1.5KB大小(使用Tiny C Compiler,它非常合適與做小型可執行程式)。
我認為,如果像Python一樣的其他語言能夠在這一點上趕上C,甚至是C的一部分,他們在嵌入式的世界中就會更加出彩。
6. 全域性變數預設是外部的(討厭)
你會說“用全域性變數可不是個好習慣!”。但在嵌入式系統中不同。舉個例子,你有一個名為timer.c的檔案,其中有個全域性變數int counter,在另一個檔案state_machine.c中,有另一個counter。如果你碰巧忘記了在它們之前加上’static’,它們就是同一個變數,你根本察覺不到,沒有Warning,沒有任何提示……
這種行為看起來十分奇怪,尤其是當關鍵字extern就在手邊的時候。不過當你熟悉static的兩種不同的意義後,就可以輕易避免這種情況了。不過這依然十分令人討厭。
7. static的兩種不同的意義(討厭)
有人能解釋一下為什麼static在函式體中和函式體外有著兩種完全不同的意義嗎?在函式體中,他表示“靜態”——“在函式呼叫過程中保持這個變數唯一”。但是在函式體外,它的意義完全改變,成了“該變數為該檔案私有的”。為什麼後者不用private或者intern呢?
8. & 優先順序低於 ==(討厭)
在嵌入式程式設計中,我們總是喜歡用if ((x&MASK) == 0)這樣的語句。但你可能常忘記寫裡面那對括號,因為感覺上,&的優先順序應該比==高。但是事實並非如此,因此必須使用這對多出來的括號。
不過,這個情況有個不錯的歷史原因。C語言誕生自B語言,而在B語言中只有&而沒有&&運算子。當Ritchie引入&&運算子時,他們希望原有的B語言端的程式碼能夠正常執行,因此使&的優先順序低於==。
9. 巨集的功能並沒有那麼強(討厭)
雖然遞迴的#include是非常棒的點子,但是,要怎麼做才能不訴諸一些費腦子的方法,輕易地做預處理迴圈呢?同樣的,有些我常遇到的情況,比如怎麼才能給程式int和string兩種格式的版本號,而同時只需要修改一個變數呢?
#define VERSION_INT 209 #define VERSION_STR "2.09"
用上面的程式碼,你更新版本號的時候總是需要修改兩個地方。而且,特殊的#和##並不能幫上什麼忙。我找到的唯一的解決則涉及了一些執行時修改。
10. 它不支援反射(討厭)
好吧,可能這只是重申了一下第9點——如果巨集系統再稍微強大一點,就不需要反射機制了。說不定我還會濫用它。不過我真正想說的是,用C語言,你不能寫出生成程式碼的程式碼。
為什麼不用C語言本身來寫前處理器呢?這會給迴圈展開,更強大的巨集機制,甚至更多IOCCC的怪點子提供無窮無盡的可能性。:-)
我認為,C語言之父能夠坦然承認C的不足之處是非常可貴的。就像Dennis Ritchie說的一樣:
“C語言行為古怪,瑕疵遍佈,但卻是一個巨大的成功。”
更多關於這點的資訊,去讀讀他的論文 The Development of the C language 吧 —— 那真是一篇值得一讀的文章。
總而言之,在自己的優勢上,C卓爾不群。
相關文章
- 關於C語言,我喜歡和討厭的十件事C語言
- 最喜歡與最討厭的程式語言
- Python與PHP的對決:誰是工程師最喜歡和最討厭的語言PythonPHP工程師
- 最喜歡與最討厭的函數語言程式設計語言情緒排名 | Scalac.io函數程式設計
- 為什麼程式設計師會有最喜歡與最討厭的程式語言?(earthly)程式設計師
- 為什麼我喜歡富於表達性的程式語言
- 為什麼我喜歡 Lisp 程式語言Lisp
- 關於 Swift,我不喜歡的幾點Swift
- 我喜歡 C++C++
- 我喜歡於一一!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
- C語言關於回撥函式和this指標探討C語言函式指標
- Stack Overflow:最令人討厭的程式語言
- 令人討厭的程式語言排行榜
- 為什麼我最喜歡的程式語言是 GoGo
- 開發者最討厭的程式語言:Perl 名列第一,PHP、Objective-C 和 RPHPObject
- 評: 為什麼我不喜歡Go語言式的介面Go
- 開發者最討厭的程式語言:PHP、Ruby 中槍PHP
- 為什麼每個人都討厭GO語言?Go
- 關於C語言結構體對齊問題的探討C語言結構體
- 關於C語言的常量C語言
- 我討厭技術猿
- 程式語言簡史:有人討厭花括號,於是發明了PythonPython
- 為什麼我不喜歡Go語言式的介面(即Structural Typing)GoStruct
- 關於大數(C語言)C語言
- 程式設計師為什麼討厭這些語言程式設計師
- 當寫C語言寫多了,自然就喜歡C++了----小話c++(1)C語言C++
- 關於C語言的位運算子C語言
- 關於C語言的面試問題C語言面試
- StackOverflow最不喜歡的程式語言排行榜 - Oreilly
- 我最喜歡的10條程式設計語錄程式設計
- C語言寫的磁碟排程演算法,歡迎大家來討論C語言演算法
- 關於最近學習的Less預編譯語言的筆記,歡迎大家一起探討~編譯筆記
- 關於C語言的簡單介紹C語言
- 關於C語言書的書名徵集C語言
- C語言關於檔案操作的命令C語言
- C語言關於多原始檔的呼叫C語言
- 關於c語言模擬c++的多型C語言C++多型
- 我不討厭JS,只是更愛CSSJSCSS