點解寫軟件咁貴? 為練總拾遺
軟件技術是否五十年不變?
朋友來訊,引述練乙錚今年四月一篇文章[0],問我意見。練總這篇文章,講香港和大陸的GDP增長,我當然不懂。(大陸的一切,我從來都不懂。)但文章裡,有一段關於寫軟件的技術,這個我反而懂。容我引述如下:
舉例說,某燕梳公司要處理大量數據,外判給一個電腦服務公司代行;為了提供這個服務,後者要購入一個新型的數據處理器,聘請一位軟件顧問工程師工作一個月。很明顯,處理器的技術進步一日千里,性價比不斷上升,但軟件編寫的技術就不會那樣突飛猛進,故此,處理同樣複雜大量的燕梳數據,50年前的硬件部分成本可能很高,佔總成本的九成;15年前,硬件技術進步了,硬件成本可能只佔總成本的一成,但編寫軟件的技術沒有大變;到了今天,硬件成本更可能佔不到總成本的1%,軟件還是得一行一行地編寫,有關技術可謂「五十年不變」!那麼,「替燕梳公司建立一個數據處理系統」這個服務的製造業技術含量本來很高,佔成本的大部分,但到後來就差不多微不足道,變成上述的補習服務一樣,主要是一種人力心智的投入,生成這個服務的效率因而不會隨着時間過去而顯著提升。
文中聲稱「軟件技術五十年不變」是一個很大膽的觀點。如果單以字面上理解,這句話一定是錯的。舉個例,如果我要寫一個程式,把輸入的資料排序(sort),三四十年前的程式大概像這樣:
.MODEL small
.STACK 1000h ; Don't skimp with stack!
.DATA
Struct0A EQU $ ; Buffer for INT 21h/0Ah (max,got,buf)
max db 100 ; Maximum characters buffer can hold (incl. CR (0Dh))
got db 0 ; Number of characters actually read, (excl. CR (0Dh))
buf db 100 dup (0) ; Actual characters read, including the final carriage return (0Dh)
Linefeed db 13, 10, '$'
GetString db 'Enter string: $'
.CODE
start:
mov ax, @DATA ; Initialize DS
mov ds, ax
; Input String
mov ah, 09h
mov dx, OFFSET GetString
int 21h
mov dx, OFFSET Struct0A
mov ah, 0Ah
INT 21h
mov si, OFFSET buf ; Base for [si + bx]
xor bx, bx ; Prepare BX for following byte load
mov bl, got ; Load length of string = 0Dh at the end
mov BYTE PTR [si + bx], '$' ; Delimiter for int 21h / 09h
outer:
dec bx ; The last character is already at the right place
jz done ; No characters left = done
mov cx, bx ; CX: loop variable
mov si, OFFSET buf
xor dl, dl ; DL (hasSwapped) = false
inner:
mov ax, [si] ; Load **two** characters
cmp al, ah ; AL: 1. char, AH: 2. char
jbe S1 ; AL <= AH - no change
mov dl, 1 ; hasSwapped = true
xchg al, ah ; Swap characters
mov [si], ax ; Store swapped characters
S1:
inc si ; Next pair of characters
loop inner
test dl, dl ; hasSwapped == true?
jnz outer ; yes: once more
done:
; Print result
mov dx, OFFSET Linefeed
mov ah, 09h
int 21h
mov dx, OFFSET buf
mov ah, 09h
int 21h
mov ax, 4C00h
int 21h
END start
; ( Credits — Source: stackoverflow ; Author: rkhb ; License: cc-by-sa 3.0 )
二十幾年前,同樣的程式用 C language 寫,縮短到二十行:
#include <stdio.h>
#include <string.h>
int main() {
int N, i, j;
char buf[100+1];
fprintf(stdout, "Enter string: ");
fflush(stdout);
fgets(buf, sizeof(buf), stdin);
N = strlen(buf) - 1; // -1 for removing newline
for (i=0; i < N; i++) {
for (j=i; j > 0; j--) {
if (buf[j] < buf[j-1]) {
char x = buf[j];
buf[j] = buf[j-1];
buf[j-1] = x;
}
}
}
printf("%s\n", buf);
return 0;
}
十年前,用 python 寫,一行就夠:
print("".join(sorted(raw_input("Enter string: "))))
誰說「軟件技術五十年不變」呢?事實上,軟件技術日新月異,從事電腦科技的人經常抱怨要花很多時間更新知識,追上潮流。潮流這東西雖然一時一樣,但整體而言,新技術的確會令編寫程式的時間大大縮短。一個好的軟件工程師隨時懂得十幾種程式語言,二十幾種軟體框架,目的只是能夠更有效編寫系統。做 IT 行業,大家都擔心如果追不上潮流會被取締。就算今天收入略勝於儕輩,面對著一身新潮技術的後進,也不知幾年後能否保住飯碗。如果有「軟件技術五十年不變」呢支歌仔唱,IT專業人士可以食老本,靠「N年經驗」自持資歷高深的老屎窟,那將會是多麼美好的事情。
服務業的產值增長速度一般而言低於製造業?
也許有人會問,既然軟件技術越來越先進,為甚麼軟件的價錢卻越來越貴?練總的文章提到「工業」和「服務業」的分別,且讓我分析一下為甚麼「工業」的成本跌得那麼快,但「服務」的成本卻相對穩定。
傳統工業,大多數都是製造商品 (commodity),然後以市價賣出。一般製造業的經營方式,是佔據有大量潛在買家的市場,用經濟規模(economies of scale)減低成本。阿當史密夫在《國富論》的經典例子,是一粒釘的製作過程。因為釘是有大量需求的商品,廠家可以把每個製作過程拆分,用分工合作的方法,減低成本。後來廠家經常使用的生產線(assembly line),就是因分工而變得可能的技術進步。分工還有一個好處,就是每個階段的工作變得很簡單,可以用機械把工作自動化。所謂工業的技術進步,與產品的需求量的關係是密不可分的。每件機器成本也不小,如果產量不大,人手製作的成本可能更低。所以,無論技術如何先進,沒有有效的規模,成本是不能夠壓下去的。
雖然電腦處理器號稱是「高科技」產品,但它的經濟模式,仍然像傳統工業。總之就是由資本家投資人才器材,用既有的方法,把商品製造出來。市面上除了英特爾公司(Intel)壟斷了高端市場,其他製造處理器的玩家都不見得吃香,因為就算是這種「高科技」工業,競爭也很大。事實上,處理器這種東西,是一種明白電晶體 (transistor) 的基本運作後,就原則上任何人都懂得堆砌出來的東西,只不過廿一世紀的處理器有幾億個電晶體而已。當技術問題被英特爾, ARM Holdings 之類的公司解決了,餘下就只不過是資金和人力資源方面的問題。製造低端的處理器,也許可以說,跟製衣業「差不多」。至於高端的處理器,雖然英特爾投放了大量資源做科研,但因為市場上對處理器的需求仍然很大,所以市場上的買家把成本攤分了,每個買家承受的成本相對很小。
為甚麼軟件這麼貴?
那麼,軟件又是怎麼回事?練總說軟件很貴。我不同意。商品化(commoditized)的軟件,其實大多數都很便宜。在經濟學的角度,它不得不便宜。軟件的複製成本近乎零。只要沒有壟斷的情況,市場對某種軟件的需求越大,它的價錢就會越低,因為它的供應沒有技術上的限制。就算微軟公司曾經一度壟斷市場,微軟的市面上的產品也不見得很貴 (起碼不是幾千萬這樣子)。這些年來,微軟花了不知多少億美元做R&D,結果視窗系統還是在幾百美元以下的價錢。
事實上,坊間免費的「開源軟件」多不勝數,例如經常用作伺服器系統的 Linux,可以隨便在網上下載,任改任用,完全免費。一般人也許不知道坊間有很多開源作業系統,功能上和視窗系統相若,都是免費的。[1] 其實,這二十年來開源軟件推動互聯網科技發展功不可沒,甚至是主因之一。軟件工程師業內有個不文規矩,就是當有人解決了一個常見的技術問題,只要不影響公司的「核心業務」,他應該把這個技術變成開源軟件,和全世界免費分享。[2]
那麼,為甚麼燕梳公司會覺得軟件很貴?能夠處理大量數據的軟件,成本是零。伺服器可以用 Linux,數據庫用 MySQL 或 Postgresql。以上都是成熟可靠,能夠處理大量數據的軟件。但燕梳公司要求的,不是「商品化」(commoditized)的軟件,而是度身訂做(made to order)的軟件。電腦服務公司接到燕梳公司的要求,也許他們會利用 Linux 或 MySQL 作為「零件」去編寫系統,或者把這些「零件」加工。在此之前,外判公司要先了解客戶的要求,把每一個細節都搞清楚,然後才可以為客戶寫一個度身訂做軟件。而這個由了解、到編程、到完成的過程,最繁複,最用時間,最用錢。你問,為甚麼不能改善這個「技術」,令價錢變得更低?這就回到根本的問題:經濟規模(economies of scale)。處理器的成本低,技術成熟,是因為同樣的處理器,可以賣給千千萬萬個客戶。燕梳數據系統貴,沒有現成的技術,是因為……世界上有幾多間大型燕梳公司?
事實上,如果三十年前要做一個今天賣幾千萬的系統,就算沒有硬件的限制,大概也是做不到的。別說數據庫技術未成熟,就算是作業系統,也沒有甚麼選擇。[3]
明白以上道理,我們就可以解釋為甚麼服務業的產值增長速度一般而言低於製造業。服務業講究為顧客度身訂造。度身訂造的服務或產品,當然不可以大量生產,以規模減低成本。產值的增速,有其市場經濟因素,不一定完全取決於生產技術的進步。單單依靠產值的增長數字去推算技術水平,有失嚴謹。事實上,資訊科技的發展,已經讓軟件行業侵佔各種「服務業」的市場,詳情可見閱宋漢生的文章《軟件吃掉世界》。[4]
軟件之所以能夠吃掉世界,其中一個原因是軟件的複製成本幾乎等於零。因此,軟件的「單位資源投入的邊際產出值」,理論上可以無限大。因此,各種用軟件科技去侵佔傳統服務業的公司相繼而起。一般人會說,美國矽谷的 startup 靠「創意」創造財富;但經濟學家應該會說,這是新科技應用在自由市場的必然結果。因為,這些軟件寫出來的系統,更快、更方便、更有效率。重點是,一旦寫好系統,每個新增用家所需的成本極小。軟件可以使「單位資源投入的邊際產出值」變得很大,所以幾十萬資金的小型startup,可以吃掉傳統行業的市場。這是每個熟悉矽谷生態的人都知道的基本常識。而矽谷能夠發展出這個生態,正正因為近十年軟件技術和資訊技術漸趨成熟,免費開源軟件提供了廉價可靠的「零件」,讓創業者可以把它們「加工」成可以招來用家的商品和服務。就以 Facebook 為例,如果世界上沒有 Linux、沒有 MySQL、沒有PHP,他就算是天才也不能夠幾年之內寫出一個全球幾億用家的網絡平台。
服務業的技術停滯了嗎?
既然軟件的技術進步了,其他服務行業呢?練總引述補習老師為例,舉證某些服務業的技術多年來未曾提升過,原文如下:
一位補習老師悉心教導一個中學生解答一道與阿基米德原理有關的浮體力學習題。可以想像,生產這個教育服務所需的原料、工具和技術,大約就是一張桌子、兩張椅子、一支鉛筆、幾張白紙、一位起碼受過良好高中物理教育的補習老師,以及她的30分鐘的時間,這無論是在18世紀的英國、19世紀末的日本、20世紀中葉的香港、還是21世紀初年的美國,都幾乎是一樣的;也就是說,這個提供補習服務所牽涉的技術,兩百多年來未曾提升過。不只是補習服務,其他教育和訓練,例如教授芭蕾舞、畫畫、園藝,訓練開帆船、當律師、修理水喉,以及大多數的私人貼身服務如修甲、跌打、老人護理、物理治療、心理治療、性服務,等等,大致上也如此。這些類型的服務,經濟學裏稱為「技術停滯的服務」
可是,這個例子忽略了幾點:
第一,香港「補習社」近年的運作模式,已經不是一個教師對一班學生,而是一個教師透過視象系統,同時教授好幾班學生。同樣30分鐘的時間,在18世紀只能教一兩個學生,在20世紀卻可以教 N 個學生。當然,18世紀的老師理論上也可以開班教幾百個開生,但如果沒有米高風的技術,只怕會嗌破喉嚨。何況,當年的交通也沒有今天方便,要聚集幾百個學生於一堂,幾乎沒有可能。所以,補習老師的技術,還是提升了一點點。
第二,對於自發學習的學生,補習老師這個服務,在資訊年代已經可有可無。以筆者個人經歷為例,我沒有正式讀過電腦,現在於某科技公司任職軟件工程師。很多人問我,我是怎樣學會這些知識。答案就是在互聯網找資訊,自己學習。在「軟件吃掉世界」的角度,補習老師的部份功能,被互聯網取替了。其實,在我的故事裡,大學傳授知識的功能,也被互聯網取替了。教育和訓練的服務,在近年發生了翻天覆地的改變。隨著互聯網的資訊越來越豐富,美國頂尖名校相繼推出免費的網上學習平台,一般大學傳授知識的價值,變得相對很低。這個年代的學生讀書只為考試,只為一張「沙紙」,大概也是市場變化之下無可奈何的結果。
第三,我們可以把「教育」這個服務,看成一種「製作某方面的人才」的「工業」。如果,因為科技的發達,連這些「人才產品」都被科技取締了,又怎麼說?其實這種事情,已經隨時開始發生。[5]你以為「教車師傅」這服務行業有「技術停滯」嗎?幾年後,Google 的自動駕駛技術可能一夜之間就把所有汽車貨車的士司機的工作都取締了。沒有司機,就不需要教車師傅。整個行業都被科技取締了,還有甚麼「服務的成本效益」可言?別以為這是天方夜譚的故事,曾幾何時,外國有一種職業叫做 “computer”。不是電腦,而是一個專門做相對簡單而繁複數學運算的人[6],這行業幾十年前因為發明了電腦而式微。如果今天沒有電腦科技,燕梳公司就要請成千上萬的 “computer” 去處理業務上的運算了。今天還沒有 “cyborg” (人類機械合體)的科技,當然不可以直接把人類的效能提升,但某些職業已經被科技所取締。根據市場定律,這個現象,必定因為新科技的成本更低,效益更高。因此,我們可以說,這些服務業的技術進步了,成本效益因為科技的進步而增加了。
練總用五十年前的著作[7]去論證某些服務業的技術五十年不變,未免有點「食古不化」,與時代脫節。也許有人會認為,私人貼身服務,例如性服務,總不能被科技取締吧?對此,我只想提出一個思想實驗:如果世界上沒有避孕套、震蛋、飛機杯、色情網站(包括cybersex),市場對傳統性服務(男女妓)的需求,及性服務的成本,會有甚麼變化?
為甚麼軟件這麼貴?
為甚麼軟件這麼貴?重要的問題,不妨再問一次。文章上面提到,度身訂做的軟件,因為沒有經濟規模,所以貴。但這種分析市場經濟的答案,不能解答一個很主觀的疑惑:真的,為甚麼軟件這麼X貴?這個問題,其實很難答,但趁這機會,我覺得要不厭其詳寫多幾句。在香港,做 IT 的行家經常投訴公司 cut cost 時首當其衝。無他,就是這些公司的高層 (包括燕梳公司),主觀地覺得 IT 專業人員維護軟件系統很貴。香港大企業的管理層也沒有哪個懂得資訊科技,以訛傳訛,「IT 系統很貴」就變成企管圈子的常識了,也難怪練總用這個做例子。
年輕一輩拍拖經常遇到一個問題:「搵食」。男朋友問:「今晚想食咩呀?」女友回答:「隨便啦,我咩都食。」言下之意,就是昨天吃過壽司,下星期約了朋友吃意粉,快餐太cheap,茶餐廳污糟,中式酒樓老套,据扒太貴,拉麵要排隊,咖喱太辣,粥粉麵飯太悶……不過,我咩都食架。
同樣道理,你問燕梳公司主管,買了個幾千萬甚至幾億的系統,有甚麼功能?「都係嗰啲啦,好普通嗟」。他當然不會跟你說他公司有幾十萬個規條,有些是法律要求,有些是公司不文規定,有些是某個秘書習慣用某種方法輸入數據,有些是部門總管異想天開的偉大發明。這些額外度身訂做的要求,也許不多,十幾廿個。十幾廿個看似簡單的要求,可能為系統增加幾十倍的複雜度,甚至更多。這並不是說系統多了幾十倍的code:軟件的行數也許只多了幾成。但程式員每寫一行code,就意味著這句code要和整個系統配合,繼續維持系統內部邏輯的一致性。軟件的確一行一行寫,但每加一個功能,所需要的時間和資源就越多。寫第一個功能的時候,通常很簡單;加第二個功能時,就要看它和第一個功能有沒有衝突的地方;加第 N 個功能時,就要回顧之前所有的功能…… 到這個時候,軟件工程師如果不是非常熟悉系統的運作,就會開忽略了一些問題,然後就變成大大小小的 bug。
為甚麼燕梳公司的主管會搞不清楚自己的系統原來如此複雜?讓我說個歷史故事:
有天,漢文帝問右丞相周勃:「國家每年有多少件刑事案件?」周勃賠罪說不知道。文帝又問:「國家的GDP是多少?」[8] 周勃又不知,背脊出汗,感到很羞愧。於是,文帝轉問左丞相陳平,陳平答:「陛下如果要問案件的事情,可以召喚廷尉;如果要問經濟,可以召喚治粟內史。我們做丞相的,只是幫陛下管治臣子而已。」文帝很滿意這個答案。(退朝後,周勃責怪陳平:「原來你個仆街仔卸膊咁叻,又唔教我!」,此乃後話,不敘。)
陳平這個答覆,解釋了為甚麼燕梳公司主管會搞不清楚自己想要的系統的複雜性。因為,升到上去,管的是人,而不是事事親為。IT 系統的本質就是把一些本來人手做的工作系統化、自動化。所以這個系統裡,就隱然包含公司每個一個員工工作的藍圖。每個員工工作的細節,他們的主管未必清楚。就算清楚,在主管心目中也是「想當然爾」的事,未必意識到其實他在職幾十年,學過的東西也不少,要原原本本把這些東西清楚說明,一點也不容易。而寫軟件,就是把要求電腦做的東西,原原本本,清清楚楚,毫無懸念地寫出來。這個工作,談何容易。
用一個比較玄妙的說法:軟件之所以貴、之所以難寫,不是因為你沒有學過程式語言,而是因為你根本不清楚自己想要甚麼。別說程式語言,就算隨便找個識字的人,用中文去描述一個簡單系統,內容不能自相矛盾,又能夠處理所有情況,只怕十居其九寫不出來。軟件工程師設計軟件之前,須把客戶要求的功能完全清楚了解,甚至他要比客戶更加清楚客戶的要求。只要能夠清晰地說出系統的每一個細節,基本上系統就已經寫好一大半,剩下的只是「打字員」的工作。
當然,電腦外判公司的客戶服務主任,被問到為甚麼某個 quotation 這麼貴,他總不能回答:「因為你都唔知自己想要乜囉!」 搵食真係艱難。慶幸我(現在)不是做外判公司……
— — — — -
- [0] 《新常態慢增長心有不爽 失產業廿五年港遜星洲》 http://forum.hkej.com/node/122115 (信報 4月20日)
- [1] 筆者正用免費開源作業系統 Debian Linux 打這篇文章。
- [2] 一般資本家可能會覺得這種「共產」的生態不可思議,但事實上,很多世界頂級的科技公司的經驗證實了這種行為除了對其他人有利,對公司自己也有不少好處。另外,關於開源軟件的經濟價值,可以參考這篇文章:http://lemire.me/blog/archives/2014/04/14/the-financial-value-of-open-source-software/
- [3] 二十年前的視窗系統每兩小時就 hang 一次機,大家忘記了這些慘痛經歷了嗎?
- [4] http://hk.apple.nextmedia.com/financeestate/art/20140213/18623760
- [5] 例如 http://www.amazon.com/The-Lights-Tunnel-Automation-Accelerating/dp/1448659817
- [6] http://en.wikipedia.org/wiki/Human_computer
- [7] 《新常態慢增長》原文【註2】
- [8] 《史記》原載「天下一歲錢穀出入幾何?」,就是今天的 GDP 吧。
(原文於 2015 年 6 月發佈,略有修輯)