簡單就是易於除錯
對於框架、庫或者工具來說,怎樣做才算是“簡單”?也許有很多的定義,但我的理解通常是易於除錯。我經常見到人們宣傳某個特定的程式、框架、庫、檔案格式或者其它什麼東西是簡單的,因為他們會說“看,我只需要這麼一點工作量就能夠完成某項工作,這太簡單了”。非常好,但並不完善。
你可能只編寫一次軟體,但幾乎總要經歷好幾個除錯周期。注意我說的除錯周期並不意味著“程式碼裡面有 bug 你需要修復”,而是說“我需要再看一下這份程式碼來修復 bug”。為了除錯程式碼,你需要理解它,因此“易於除錯”延伸來講就是“易於理解”。
抽象使得程式易於編寫,但往往是以難以理解為代價。有時候這是一個很好的折中,但通常不是。大體上,如果能使程式在日後易於理解和除錯,我很樂意花更多的時間來寫一些東西,因為這樣實際上更省時間。
簡潔並不是讓程式易於除錯的唯一方法,但它也許是最重要的。良好的文件也是,但不幸的是好的文件太少了。(注意,質量並不取決於字數!)
這種影響是真是存在的。難以除錯的程式會有更多的 bug,即使最初的 bug 數量與易於除錯的程式完全相同,而是因為修復 bug 更加困難、更花時間。
在公司的環境中,把時間花在難以修復的 bug 上通常被認為是不划算的投資。而在開源的環境下,人們花的時間會更少。(大多數專案都有一個或多個定期的維護者,但成百上千的貢獻者提交的僅只是幾個補丁)
這並不全是 1974 年由 Brian W. Kernighan 和 P. J. Plauger 合著的《程式設計風格的元素》中的觀點:
每個人都知道除錯比起編寫程式困難兩倍。當你寫程式的時候耍小聰明,那麼將來應該怎麼去除錯?
我見過許多看起來寫起來“極盡精妙”,但卻導致難以除錯的程式碼。我會在下面列出幾種樣例。爭論這些東西本身有多壞並不是我的本意,我僅想強調對於“易於使用”和“易於除錯”之間的折中。
- ORM 庫可以讓資料庫查詢變得簡單,代價是一旦你想解決某個問題,事情就變得難以理解。
-
許多測試框架讓除錯變得困難。Ruby 的 rspec 就是一個很好的例子。有一次我不小心使用錯了,結果花了很長時間搞清楚究竟哪裡出了問題(因為它給出錯誤提示非常含糊)。
我在《測試並非萬能》這篇文章中寫了更多關於以上的例子。
-
我用過的許多 JavaScript 框架都很難完全理解。Clever(LCTT 譯註:一種 JS 框架)的語句一向很有邏輯,直到某條語句不能如你預期的工作,這時你就只能指望 Stack Overflow 上的某篇文章或 GitHub 上的某個回帖來幫助你了。
這些函式庫確實讓任務變得非常簡單,使用它們也沒有什麼錯。但通常人們都過於關注“易於使用”而忽視了“易於除錯”這一點。
-
Docker 非常棒,並且讓許多事情變得非常簡單,直到你看到了這條提示:
ERROR: for elasticsearch Cannot start service elasticsearch: oci runtime error: container_linux.go:247: starting container process caused "process_linux.go:258: applying cgroup configuration for process caused \"failed to write 898 to cgroup.procs: write /sys/fs/cgroup/cpu,cpuacct/docker/b13312efc203e518e3864fc3f9d00b4561168ebd4d9aad590cc56da610b8dd0e/cgroup.procs: invalid argument\""
或者這條:
ERROR: for elasticsearch Cannot start service elasticsearch: EOF
那麼…你怎麼看?
-
Systemd
比起SysV
、init.d
指令碼更加簡單,因為編寫systemd
單元檔案比起編寫shell
指令碼更加方便。這也是 Lennart Poetterin 在他的 systemd 神話 中解釋systemd
為何簡單時使用的論點。我非常贊同 Poettering 的觀點——也可以看 shell 指令碼陷阱 這篇文章。但是這種角度並不全面。單元檔案簡單的背後意味著
systemd
作為一個整體要複雜的多,並且使用者確實會受到它的影響。看看我遇到的這個問題和為它所做的修復。看起來很簡單嗎?
via: https://arp242.net/weblog/easy.html
作者:Martin Tournoij 選題:lujun9972 譯者:LuuMing 校對:wxy
訂閱“Linux 中國”官方小程式來檢視
相關文章
- NASM 與 GDB 簡易除錯指南ASM除錯
- Kdevelop的簡單使用和簡單除錯dev除錯
- Node.js 簡單除錯Node.js除錯
- 簡單的沙箱反除錯除錯
- Google Chrome 除錯JS簡單教程GoChrome除錯JS
- Linux—gdb除錯簡單實現Linux除錯
- 簡單選擇排序就是簡單~~~排序
- Laravel 一個簡單的除錯工具Laravel除錯
- VS斷點除錯簡單筆記斷點除錯筆記
- 單例模式就是如此簡單單例模式
- CVE-2015-7547簡單分析與除錯除錯
- 原來 Java 遠端除錯如此簡單Java除錯
- jdbc就是這麼簡單JDBC
- WebSocket就是這麼簡單Web
- WebService就是這麼簡單Web
- jwt 就是這麼簡單JWT
- ThreadLocal就是這麼簡單thread
- SpringBoot就是這麼簡單Spring Boot
- Activiti就是這麼簡單
- 逮蝦戶!Android程式除錯竟簡單如斯Android除錯
- promise原理就是這麼簡單Promise
- 除錯Kubernetes工作負載的最簡單方法 - Martin除錯負載
- Spring AOP就是這麼簡單啦Spring
- 建造者模式就是這麼簡單模式
- C++簡單日誌/debug除錯資訊輸出C++除錯
- 搞定JVM垃圾回收就是這麼簡單JVM
- Mybatis【配置檔案】就是這麼簡單MyBatis
- HashMap就是這麼簡單【原始碼剖析】HashMap原始碼
- Spring【DAO模組】就是這麼簡單Spring
- Spring【依賴注入】就是這麼簡單Spring依賴注入
- Spring【AOP模組】就是這麼簡單Spring
- 包裝模式就是這麼簡單啦模式
- JSP自定義標籤就是如此簡單JS
- 二叉樹就是這麼簡單二叉樹
- python如何單步除錯Python除錯
- [譯] 使用 VS Code 除錯 Node.js 的超簡單方法除錯Node.js
- 網易雲簡單案例
- kotlin代理模式就是這麼簡單(委託)Kotlin模式