Lua 程式設計教學:分裂的 Lua 世界

Lua 不是一個主流的語言,不過還蠻常見的,主要用於遊戲引擎 (game engines) 和其他軟體的腳本語言 (scripting language)。本文的目的在說明 Lua 的特性及這些特性對 Lua 社群的影響。

Lua 最重要的概念在於 Lua 是一種內嵌語言 (embedded language),而和一些大而全的通用型腳本語言,如 Python 或 Ruby 等,不同。對於 Python 或 Ruby 等主流語言來說,會有一個主要的實作品 (implementation) 加上標準函式庫 (standard library),不足的再由第三方套件 (third-party packages) 加強其功能。但 Lua 是包在其他宿主軟體 (host software) 內,由宿主軟體來提供功能;像是 Corona 和 Cocos2d-x 這兩套遊戲引擎都使用 Lua,但兩者的 API 卻不互通。此外,Lua 的套件不僅相對少,而且不同宿主軟體間的套件無法通用,通常都是由各位宿主軟體各自提供插件 (plugin) 來擴充其功能。因此,Lua 社群是分裂的。

為什麼會使用 Lua 這種內嵌語言出現呢?假設我們現在在開發一個電腦遊戲,如果我們將所有的遊戲參數都寫死在 C++ 程式碼中,當我們要更動某些遊戲參數時,必需要重新編譯我們的程式;中大型的 C++ 程式,每次編譯都要耗費不短的時間,無形中造成開發效率的低落。如果我們將一些遊戲參數等非效能瓶頸的部分抽離出來,寫在 Lua 命令稿中;當我們要修改參數時,只要更動相關的 Lua 命令稿即可,無形中減少不少編譯軟體的時間,也更利於分工。

除了內嵌的特性以外,Lua 版本的差異也造成 Lua 社群更加分裂。Lua 在 5.1 版至 5.2 版之間進行了一些不相容的更動,不僅在於 Lua 的語法本身,也在於其 C API,如果想要軟體內嵌的 Lua 升級,勢必要更改一部分內容。另外,Lua 除了官方的版本外,還有一個非官方的 LuaJIT,而 LuaJIT 的 Lua 版本約略在 5.1 至 5.2 版之間。有趣的是,LuaJIT 的效能還比官方的 Lua 版本佳,差距可達到 5 至 50 倍之間。雖然官方的 Lua 版本已經來到 5.3 版,但很多軟體仍然停留在 5.1 版或是 LuaJIT 版,這是在大部分主流語言少見的現象。

對於 Lua 學習者來說,要如何因應呢?追隨 Lua 版本的變動不是最重要的,選擇自己所需的宿主軟體,使用該宿主軟體所對應的 Lua 版本即可。以撰寫遊戲軟體來例,在開始撰寫遊戲前,先將該引擎提供的 API 大略瀏覽一次,並閱讀其插件手冊,了解相關的功能是否符合自己的需求,再開始撰寫遊戲,像是 Corona SDK 適合 2D 或 2.5 D 遊戲,但對於 3D 遊戲就無能為力;由於各個宿主軟體的 API 不相容,換宿主軟體等於一大部分的程式碼要重寫,所以,一開始時就要選好適合自己的遊戲引擎。

如果只是想先學一下 Lua 的語法,那麼,選擇 5.1 版或是 LuaJIT 是較佳的選擇。新版 Lua 所帶來的新語法特性,相對來說不是那麼重要;而且,許多軟體其實沒有將其內嵌的 Lua 版本更新,或是使用 LuaJIT。所以,即使 Lua 5.1 版有點舊了,筆者仍然推薦從這個版本開始學習 Lua。

對於想要將 Lua 內嵌於自己軟體的開發者來說,要使用那個版本呢?理論上,任何一個版本皆可;如果很在意效能的話,使用 LuaJIT 是比較好的選擇;如果使用官方版 Lua,就沒有必要守在 5.1 版了,大可使用最新的 5.3 版。

經過本文的介紹,相信讀者已經對 Lua 有一些基本的概念。筆者在本系列文章,以 Lua 語法本身為主,對於特定的 Lua 相關軟體,如 Corona 或 Cocos2d-x,則不在範圍中;有機會的話,或許日後會介紹。在下一篇文章中,我們會建置 Lua 開發環境,為撰寫 Lua 程式作準備。