給程式設計師的Vim入門圖解說明

12-09 Update: The English version of Vim Visual Cheat Sheet is also available.PNG,PDF)(更新: 在圖內加入基本指令表和說明以及PDF版,方便大家列印出來貼在牆上隨時查看。)剛在寫那篇關於vi和文字編輯器的文章時,本來想附上一個vim的超簡單入門連結,但找了一下都沒有很滿意的,所以決定自己動手先來畫個入門用的說明圖。vim-cheat-sheet-fullPDF版下載vim-cheat-sheet-diagram這個圖把vim中基本的移動方法都畫上去了,為...閱讀全文

Vim的多行編輯

之前看TextMate的Demo影片,發現TextMate能同時對多行做修改(例如,在連續十行的開頭結尾都加上<li>和</li> tag),就一直在想vim能不能做到這樣。一直以來我在vim中都是用V把要修改的範圍選出來,再用s///搭配regular experssion做取代。這方法彈性很高,但大多時候是殺雞用牛刀,太麻煩了。還好剛發現一個vim tip裡寫到一個簡便的新方法。簡單來說,用ctrl-v做blockwise的visual selection時,按下大寫I,就能對所選範圍同時插入一樣的文字;而按大寫A,則是在所選範圍後同時append同樣的文字。閱讀全文

Vim + Visual Studio .NET on Windows

像我這種用習慣vim的人,不論用甚麼其他的編輯器都會渾身不對勁,更別提還要拿來寫程式。因此我排斥Visual Studio已經不是一天兩天的事了,但這學期修了個Game Programming,很不幸的它提供的Game Engine只能在Windows下跑...這讓我不想用Visual Studio也不行了 :((呃,我知道MinGW啦,但我並不想花太多力氣搞MingGW+DirectX+Game Engine的相容問題...)所以呢,我得在Windows上裝vim,然後讓我能在vim中compile & test程式。以前的Visual Studio可以用一個叫VisVim的plugin,但VS .NET後就不能用了。另外,以前還能export makefile出來,現在似乎也不行了...!#*(!#&!&%@$研究了半天,發現我得透過"Microsoft Visual Studio .NET 2003/Common7/IDE/DevEnv.com"這個程式,才能在command line底下build program。底下是給vim的設定,我把這個設定加在vim的session file中,這樣之後再開project就不用一直重設,而這個設定也不會干擾到其它檔案了。set makeprg=devenv.com /Build Debug xxx.slnset errorformat= %#%f(%l) : %#%t%[A-z]%# %m(xxx.sln請自行換成你的.sln檔。DevEnv.com的PATH也要先設好。)這樣就能在vim下用:make來build程式,並且vim也能parse錯誤訊息並自動跳到對應的那一行了。只是有一點我還搞不定,devenv的help說用/LCID能設定它的locale,但我怎麼設都沒用,跑出來的訊息一直都是中文的,這讓我在UTF-8 term下面老是看到一堆亂碼..。閱讀全文

TextMate, snippetsEmu for Vim

在Mac OS X上有一個傳說中的text editorTextMate,它因為在Ruby On Rails demo上頻頻曝光,於是突然爆紅起來,甚至傳出有人為了這個editor而買了Mac的消息。我在第一次看到那個rails demo時,也注意到了presentor用的editor似乎非常神奇,不但能打幾個字就生出"整塊" code block template,而且還能非常流暢的把template填完。後來去查了一下,才發現原來這個editor叫TextMate,而那個神奇的auto-complete功能叫做snippet。TextMate雖然真的很好用,但目前還有個致命缺點:它竟然不能正確處理中文!!更精確的說,它會把中文字的寬度當成一般ascii字元的寬度來看,所以打中文上去就會發現字都疊在一起了。除此之外,OpenVanilla的選字窗在上面也是完全看不見的。因為如此,我還是只能繼續用我的Vim。(其實,即使TextMate的中文沒問題,我應該也還是換不過去吧,除非它支援Vi的key binding....) 雖然TextMate不太合用,但我還是對snippet念念不忘。剛用Google查了一下,發現跟我有同樣怨念的人還真不少,而且早就有人寫了Vim的snippetsEmu,也就是能讓Vim也有一樣功能的plugin!snippetsEmu的用法還蠻簡單的,把它的.vim抓下來放在.vim/plugin/裡,接著在.vimrc中設定一行let g:snip_set_textmate_cp=1就能開啟TextMate的相容模式,也就是一直按tab就行了。但只有這個東西還不太夠用,目前還缺少各個語言的snippet file,如果有人知道哪裡有蒐集或是有自制的請通知我一聲。我目前已知的snippets有:BTW, Emacs也有類似的plugin,可以參考這篇文章: http://gugod.org/blog/2006/01/emacs-my-snippetel.html閱讀全文

為什麼我用Mac

這篇文章其實已經醞釀很久了。起因是前幾個月看了tinyfool的为什么我认为每个程序员都应该用Mac OS X?youxu的开发人员为何应该使用 Mac OS X 兼 OS X 小史,我當時就很想順便分享一下我的經驗,但那時忙著Sikuli實在沒法靜下心來寫文章,直到最近稍微閒下來了才又想起這件事。我從2005升上研究所前買了第一台Mac mini到現在已經五年了,說起來其實沒有很長,但自從2005年起,我就成了非Mac不用一族。但用Mac是一回事,我要先澄清我不算是狂熱的Apple粉絲,我除了Apple的電腦外,只有跟朋友以超低友情價買過一台開學優惠送的ipod touch來玩,除此之外,我沒有iphone、沒有ipad、也沒有Apple鍵盤滑鼠以外的周邊產品。在2005年以前,我高中和大學約6年都是用Linux作為主要工作環境。我一路從Slackware、RedHat、Mandrake(後來改名Mandriva)、玩到Debian、Ubuntu,那段時期我有數台24hr online的Linux server,還換過3台laptop,但都是裝Linux。在更之前呢,從國小的386 PC算到高一將近10年就是用DOS和Windows了。這篇文章主要想分享的是作為一個programmer使用各種作業系統開發的經驗,不是想要說服大家全改用Mac。雖然從時間上看起來我用DOS和Windows最久,但我真正開始大量寫程式是國中開始用Visual Basic的事,所以我在DOS和Windows平台的開發經驗其實算是最少的。而大學階段是我最密集寫程式的時候,所以我的經驗和使用的工具也都是以UNIX派的為主,不見得適用所有人。我在DOS+Windows、Linux、Mac這三大主流平台上都混過一段時間,這個遷徙的歷史其實也代表了我個人心態上的轉換。在剛開始學電腦的時候,我是純粹的使用者。我用電腦玩遊戲,國中幫老師用excel做全班的成績單,閒來無事就隨手玩玩photoshop、3D studio等軟體自娛娛人。我記得在386的DOS時代要玩個遊戲還挺不簡單,雖然很多遊戲都說只要打play.bat就可以玩了,但事實上總要修改config.sys和autoexec.bat裡的一些記憶體或音效卡的設定才能玩。所以那個時代的使用者其實大都是玩家級的人物,多少都對Adlib、EMS、XMS、可恨的640K限制有些了解才有辦法「玩」電腦。國中開始寫程式之後,我的心態就不太一樣了。像一般玩家般玩電腦已經不能滿足我,我開始熱切的想了解電腦內部運作的一切原理,想了解每個程式是怎麼寫出來的,每個零件是怎麼運作的,每一個細節我都想知道。而我剛好就在這段時間接觸到Slackware Linux。Slackware Linux其實是一個不太好用的Linux distribution,可能很多人也沒聽過它。現在的Ubuntu和Windows沒兩樣,一直按「next」就能裝完整個系統並開始使用。但那時的Linux裝完後可是「什 麼 都 沒 有」。沒有X11,更別提其上的GNOME或KDE;文字編輯器只有vi(不是vim)和joe;沒有make、沒有gcc、...,總之,真的什麼都沒有。那個時候裝Linux其實是為了自己架MUD server,但當時Linux的安裝教學都說裝完的一件事就是自己重新compile kernel。(因為預設的kernel很陽春,幾乎什麼driver都沒有,不自己compile的話很多硬體都動不了。)其實當時我覺得這還蠻酷的,make config打完出現數百個選項可以慢慢勾選,讓我這種想要一窺作業系統裡面在搞什麼鬼的人非常過癮。(一開始我還不知道有make menuconfig可以用,所以其中一個選項不小心選錯就會非常痛苦要整個重來......)但過了一段時間我就發現,MUD server沒架起來,但倒是很會重編Linux kernel和設定xf86config。國中我還在用Visual Basic寫程式時,其實沒有注意到「平台」不同的影響,因為當時我只用Windows和VB寫程式,也不會其他語言,更不用提在不同平台寫程式。一直到上高中學了C,開始寫比賽的程式時,才讓我注意到Turbo C和gcc雖然都可以compile C的程式,但有某些header檔(像是conio.h)是只有Turbo C中才能用的。發現這件事後,我才突然搞懂library是什麼,還有Linux下有一堆libxxxx及libxxxx-dev的套件是在做什麼的。Windows和Linux的關鍵差異 - 資訊透明度 - 也就在這裡顯現出來。在我學VB的時候,我把當時一本VB5的經典書籍從頭到尾全讀過了,但我竟然對library一點概念都沒有。我以為我能用的東西就是VB提供的那些元件,後來我多學了一點後發現我還能呼叫Windows API做一些VB辦不到的低階功能,我從來沒想過要去利用別人已經寫好的程式和函式來節省自己的開發時間。簡單說,我以為要造一輛車子,就是要從輪子甚至是螺絲釘自己做起。某方面來說這是個好事,因為我的第一個VB遊戲「黑白棋」,就是這樣一個個pixel從無到有自己畫出的。但如果要寫更大的程式,每次都從輪子做起就不是個好主意了。接觸到Linux後,我也學了很多open source界的「哲學」,其中最重要的就是重用別人的輪子。記得很久以前在Redhat和Mandrake上裝軟體非常痛苦,雖然每個程式都被包裝成一個RPM檔,但RPM之間的相依性常會讓人發瘋。每裝一個軟體都有可能會跳出數個相依的library或套件需要安裝,然後使用者必須自己去找這些相依的RPM,更糟的是這些相依套件可能會沒完沒了的依賴更多其他的套件...。(還好後來改用Debian就不用再被這個RPM地獄折磨了。)這個過程讓我深刻的體會到,軟體應該是像金字塔一樣一層疊著一層往上蓋的,Linux套件的包裝方式清楚的讓使用者能夠看出來一個軟體是利用了哪些library建構起來的,如果自己想寫有類似功能的程式,很容易就可以找到相關的library來用。但在Windows下就不是這麼一回事了。Windows的軟體是為end-user設計的,目標使用者很可能什麼都不懂,所以發佈軟體時應該要把所需要的library或套件全部包進去變成一個龐大的自動安裝程式,使用者只要一直按下一步就可以裝完了。這讓使用者變得比較輕鬆,但同時也一些對開發者有益的細節也隱藏起來了。Windows的軟體大多是完全不透明的,安裝時你不知道它裝了什麼,也不知道它寫了什麼到registry,更別提要知道他的某某功能是怎麼做的。但Linux是在另一個極端,每個程式的一切都是透明易懂的,RPM或DEB套件裡有什麼東西一個指令就一清二處,每個套件需要用到哪些相依套件也是明明白白。此外,Linux下的設定檔都是純文字,只要文字編輯器就可以修改,不但方便編輯,也方便寫自動化的script或是備份系統。當然,更不用提Linux下幾乎所有程式都是open source的,只要有興趣,隨時可以打開每天在用的軟體的source研究它是怎麼做的。這些事情在Windows底下則是天方夜譚,所有的細節都被自然的包裝和隱藏起來了。這種透明度的差異對於充滿好奇心的程式設計師會產生南轅北轍的影響,當你接觸的東西越開放,就能自然而然接觸和學習電腦從裡而外的各種知識;但當你接觸的東西越封閉,就只能受限於黑盒子的限制而當個單純無知的使用者。高中時轉到Linux作為工作環境還有另一個很大的原因:「效率」。Linux的世界是架構在文字設定檔和command line工具上的,整個OS的操作都可以用command line解決。更方便的是搭配shell script或是Perl、Python這種script language,可以輕易把系統裡各種小工具結合起來完成複雜的工作。command line有個很大的好處,你每天用的操作介面,和寫自動化script的介面是完全一樣的。也就是說,你只要把每天打的指令串起來放進一個檔案,就自然變成了shell script,而日後只要執行這個script就能自動完成需要一連串指令的工作。這種工作方式滿足了我身為一個「懶人」的慾望,因為我懶得每天用手親自重複做同樣的事情,所以我寫script將這些事自動化。當script寫的越多,就會面臨越複雜的工作,這時就會想要學更多"UNIX power tools"的用法(這是O'REILLY的一本好書)或是更強大的「黏合」語言(像是Perl)來組合不同工具。透過這種正向循環,可以不斷刺激自己提昇工作效率:事情做得越快,就可以想得更多,解決更複雜的問題,進而就能學得更多,做得更快。大學那幾年我成了虔誠的Linux command line信徒,不管是什麼樣的事情我都可以用各種小工具加上Perl或shell script來解決,而Windows在這方面就完全比不上Linux。Windows的哲學是一套軟體可以做N種事情,但如果你想做的事情不在它原本設計的功能裡,只能兩手一攤什麼事也做不了。資訊的透明度和command line帶來的高效率讓我非常享受在Linux上工作的樂趣,然而Linux也不是沒有缺點。當我學得越多,對系統底層的好奇心漸漸被滿足後,Linux的缺點就漸漸暴露出來,其中最讓我受不了的是殘破不全的driver支援。讓我印象最深刻的是在802.11b無線網路剛開始流行時,我花了很多時間在找driver和當白老鼠compile最新的driver,重編kernel幾乎是每日例行公事。除了無線網卡外,就算是有線網卡Linux都不見得支援,最惡名昭彰的莫過於Dlink系列的卡,他們的530TX甚至還被暱稱為惡魔卡。(這張便宜的卡在當時非常流行,但偏偏在Linux上就是不能用...)雖然我是個programmer,但我同時也是一般user。在我想要快樂用電腦看電影或上網時,還要不時的處理系統內部的問題其實有點惱人,更別提當我只想寫一般的桌面程式或是Web app時,為什麼我還得跟Linux kernel奮戰呢?除了硬體相容性外,Linux這種過於開放的平台還有個大問題是缺乏統一且一致的user experience design,導致usability常常奇差無比,而這也是很多open source軟體普遍共有的問題。程式設計師在乎的是功能面的設計,每個人做自己想要或喜歡的功能,雖然看起來和樂融融,但很少project有專門的團隊負責思考user是誰,他們想要什麼,以及他們會怎麼用這個軟體。同樣的功能但由不同的介面呈現,帶給使用者的感覺也會有天南地北的差異,而由千百個open source軟體拼湊起來的Linux系統帶給使用者的就是千百種不同的設計和使用方式。(後來Ubuntu的出現大大的改善了這個問題,但那時我早已跳到Mac上了...。)就在Linux的缺點慢慢浮現後,我同時也注意到身邊很多FreeBSD/Linux hacker們開始改用Mac OS X。深入了解後,我很快發現Mac是一個完美解合Linux的效率和開放,同時又兼顧了精心設計過的user experience design的平台。Mac作業系統核心是BSD的近親Darwin,上層有跟Linux相同的command line shell,所以我以往在Linux慣用的設定檔和程式(bash、screen、vim...)全都可以直接帶到Mac上使用。(更棒的是還能像在Debian下一樣用apt-get install或是port install一個指令就自動裝完所有相依套件)而在command line的上面則是Apple設計的GUI系統,美觀、一致、充分為使用者「設計」過的介面,輕易的就打敗我在Linux上較調半天的FVWM設定。(我換過和較調過無數的window manager,從enlightenment、GNOME、KDE、Window Maker、FVWM...)除此之外,我也不用再自己重編kernel和找driver,每一台Mac都是買來後一打開就能用了。後來Mac用久了,漸漸發現更多Mac的好處,尤其是對於programmer而言。每一台Mac都有附Mac OS X的安裝光碟,裡面同時附帶Xcode。而只要把Xcode裝上去後,我整台Mac就已經準備好可以讓我工作了。Xcode是Apple開發的IDE,可以開發各種常見的程式語言,但其實我不用這個。我都用Xcode底層的command line工具,像是gcc、make、svn,加上OS X內建的screen、vim、perl、python、apache(只用這些的話其實連Xcode都不用裝,每一個OS X都內建),我就有了完整的程式開發環境,而且我甚至還不需要連上網路就可以有這些。除此之外,Xcode裡還附帶很多好用的開發、除錯工具,像是我最愛的Shark(非常好用的profiling和memory debug工具)、或是Malloc Debug(找memory leak的好東西)、BigTop(監看每一個process耗用的資源記錄)。自從我轉到Mac後,後來因為需要寫跨平台程式而切到Windows時,都覺得極端痛苦。因為Windows是給一般使用者的系統,而且所有程式都是獨立分開的,每次光要把開發環境準備好就要先耗上一整天在下載和安裝。後來我學乖了直接裝cygwin弄一個假的UNIX環境出來,但cygwin畢竟還是跑在Windows上,系統設計的哲學不同讓cygwin還是格格不入。(像是Windows就是沒有用文字檔存放系統設定,所以也沒辦法用一般的文字工具自動操作;Windows也沒有提供夠多的command line工具可以控制系統;Windows也沒有符號連結(symbolic link),我之前想用Bazaar check out一個有符號連結的repository就爆炸了...)從Linux轉到Mac,讓我可以花更多時間專注在我想寫的程式上,而不是拿去研究driver的相容問題,或是Linux kernel新增的設定選項。對於一個應用程式或網頁程式的開發人員來說,這些底層的細節都是不重要的。雖然說Windows也把系統底層的細節藏起來了,但它實在藏的太徹底了。萬一偶爾需要看系統底層的訊息來debug,在Mac上還是跟Linux一樣直接到/var/log下grep一下就有了,但在Windows上除了「回報給微軟」外,也沒太多辦法可以自力救濟。Mac上很多設計也改變了我使用電腦的方式。例如說QuickSilver讓我可以用鍵盤快速啟動任何程式,甚至是做更複雜的操作。Spotlight讓我不再需要思考怎麼把檔案文件分類整理到不同folder裡,需要什麼就像用google一樣只要直接用spotlight找就好了。Mac上的繪圖、設計軟體都有很貼心的設計,例如OmniGraffle的自動對齊線,可以幫忙使用者輕易設計出平衡、一致、美觀的圖像、網頁、或是圖形介面。Mac上幾乎什麼都可以自然地用drag and drop操作(例如Safari很早以前就可以把檔案拖到網頁裡上傳),但很奇怪Windows上就是有些地方可以有些不行。整體來說,Mac是一個融合Windows和Linux雙方優點的平衡點,我可以像一般使用者一樣不費心力的操作電腦,也可以用高效率的command line處理複雜的任務,甚至是在需要的時候扮演hacker挖掘底層的錯誤訊息,或是利用Darwin Ports安裝和修改我需要的open source軟體。但除了Mac外,其實我還是有在用Linux,只是都跑在遠端的server上而已。主要原因是在沒有圖形介面時,Mac就沒有什麼優勢了。所以到現在即使我的laptop都改用Mac,我也還是會有一個terminal連到我的Linux server上。(雖然說主要是拿來掛IRC和BBS的...)閱讀全文

贊助vgod

如何贊助

您可以使用信用卡透過下面的PayPal "Donate"按鈕贊助我。如果您想使用ATM轉帳,也歡迎來信(vgod _at_ vgod.tw)跟我索取台灣或美國的銀行帳戶資訊。金額不限,請依照自...閱讀全文