歡迎訪問 Lu程序設計

Lu功能特點

目  錄

1 什么是Lu

2 在軟件中加入腳本支持

3 Lu是一個輕量級的動態庫
4 Lu可對字符串表達式直接編譯運行
5 Lu語法簡潔,是一種字符流,可自定義注釋
6 Lu有很高的運行效率
7 Lu有五種變量
8 Lu有豐富的運算符和數據類型
9 Lu支持自定義數據類型和運算符重載
10 Lu支持模塊化編譯,支持對私有數據的保護
11 Lu使用命名空間避免函數重名
12 Lu有很強的擴展性
13 MLu簡化了Lu腳本的使用
14 Lu提供自動內存管理,也可以手動管理內存
15 Lu混合編程中對象操作特點
16 Lu支持協程
17 Lu是動態強類型的
18 Lu支持中文編程
19 Lu是可移植的

1 什么是Lu [返回頁首]

  Lu是一個可對字符串表達式進行動態編譯和運行的動態鏈接庫(dll),是一種易于擴展的輕量級嵌入式腳本,提供自動內存管理,也可以手動管理內存。Lu有豐富的運算符和數據類型,大多數運算符可進行重載。Lu的優勢在于簡單易用和可擴展性強。Lu可用于各類數學軟件的設計,也可用作報表處理、web、組態軟件、游戲等的腳本,具有很高的執行效率。

  Lu來源于Forcal,可以說,沒有Forcal就沒有Lu,但學習Lu并不需要了解Forcal。Lu是對Forcal的完善和發展,但與Forcal相比,Lu更簡潔實用。Forcal是弱類型的,但Lu是強類型的。

  Lu用stdcall調用協議輸出了動態庫函數,可供C/C++、VB、delphi、FORTRAN等程序使用。

    下載試用:lu32.rar

2 在軟件中加入腳本支持 [返回頁首]

  很多軟件中提供了腳本支持,例如Excel、Word中使用了VBA;Matlab、Mathematica、MapLe等數學軟件中有自己的內嵌腳本;**世界等許多游戲中使用了Lua腳本;組態軟件中常使用VBA、JavaScript等腳本;... ...。

    通常,應用程序通過窗口提供菜單、按鈕、鼠標操作供用戶選擇功能,如果這些不能滿足要求,就需要借助于腳本了。利用腳本語言進行功能擴充和二次開發是未來軟件開發的趨勢。

    腳本的表現形式是字符串(或者說腳本表現為一行或多行字符),這是腳本在軟件設計中受歡迎的根本原因。

3 Lu是一個輕量級的動態庫 [返回頁首]

    Lu是一個動態鏈接庫(dll),在32位windows平臺上是lu32.dll(相應地,在64位windows平臺上是lu64.dll),lu32.dll稱為Lu的核心庫 ,大小約220K~300K,是輕量級的。Lu用stdcall調用協議輸出了動態庫函數,可供C/C++、VB、delphi、FORTRAN等程序使用。Lu提供了約30多個輸出函數,但常用的只有幾個。使用Lu的輸出函數相當于進行API(Application Program Interface)函數調用。

4 Lu可對字符串表達式直接編譯運行 [返回頁首]

    許多腳本語言需要將腳本文件保存為磁盤文件才能調用,例如Lua腳本文件的擴展名為“.lua”,Python腳本文件的擴展名為“.py”,Matlab腳本函數的擴展名為“.m”,等等。雖然這些腳本也能直接編譯運行字符串形式的表達式,但通常會有這樣或那樣的限制,或者效率較低。

    Lu可對Unicode字符串表達式(字符串中可定義一個函數)直接編譯運行。Lu的輸出函數中,LuCom用于編譯一個字符串,返回一個句柄p;LuCal用于執行句柄p,可執行任意多次。注意這里所說的編譯與C/C++的編譯不同,Lu的編譯是將字符串表達式編譯為LuCal可執行的中間代碼。

    參考:Lu編程指南

5 Lu語法簡潔,是一種字符流,可自定義注釋 [返回頁首]

    簡單的Lu表達式:

1+2

    定義一個函數f:

f(x,y)=x+y

    函數調用:

f(1,2)

    所有的Lu代碼都是字符串形式,稱為字符串表達式,字符串表達式中可定義一個函數,例如前面定義的函數f。

    類似于C/C++,Lu代碼是一種字符流,該字符流是由逗號隔開的若干語句組成,例如下面定義的函數test(這是一段有關八皇后問題的代碼,不理解沒有關系):

test(row, ld, rd : pos,p : sum,upperlim)=
{
    which
    {
        row != upperlim,
        {
            pos = {upperlim && [!!(row||ld||rd)]},
            while{ pos,
                p = pos&&(-pos),
                pos = pos -p,
                test[row+p, (ld+p)<<1, (rd+p)>>1]
            }
        },
        sum++
    }
}

    也許你發現似乎有些地方缺少逗號,但這是一種錯覺,注意test、which、while是函數,其余的標識符row、ld等是各種變量,另外,最后一個語句后是不能有逗號的。

    該函數可在一行中進行定義:

test(row, ld, rd : pos,p : sum,upperlim) = {which{row != upperlim, {pos = {upperlim && [!!(row||ld||rd)]},while{ pos,p = pos&&(-pos), pos = pos -p, test[row+p, (ld+p)<<1, (rd+p)>>1] }}, sum++ }}

    很遺憾,核心庫lu32.dll支持的Lu源代碼中不能包含注釋,不過,這個缺點恰恰也是Lu的優點,你可以自己定義注釋的形式,在用LuCom編譯源代碼之前,自己去掉注釋即可(將注釋字符全部用空格代替)。

    個人比較喜歡C++風格的注釋,故在Lu模塊化編譯運行庫MLu中使用了這種注釋。

    參考:Lu用戶指南

6 Lu有很高的運行效率 [返回頁首]

    參考:Lu與C/C++、Forcal、MATLAB、Python、Lua等各種語言的速度比較

    在主程序和Lu系統之間頻繁穿越時,仍有很高的效率,參考:C/C++操作Lu腳本變量

7 Lu有五種變量 [返回頁首]

    Lu有五種變量,即:自變量、動態變量、靜態變量、模塊變量和全局變量。

    自變量、動態變量和靜態變量只能被定義該變量的表達式所訪問;模塊變量可被同一模塊的所有表達式所訪問,其他模塊的表達式無法訪問(Lu支持模塊化編譯);全局變量可被所有的表達式所訪問。

    自變量用于向表達式傳遞參數,因此自變量也稱為形式參數。動態變量只在表達式執行時起作用,一旦表達式執行完畢,動態變量也隨之失效。靜態變量存在于表達式的整個生命周期,每次表達式執行完畢,靜態變量的值被保留。

    Lu在編譯表達式時,自變量不進行初始化;動態變量初始化為nil;靜態變量初始化為0;模塊變量和全局變量在第一次生成時初始化為nil,以后使用不再進行初始化。

8 Lu有豐富的運算符和數據類型 [返回頁首]

表1:Lu運算符及優先級(僅供了解使用)

運算符類型

運算符 名稱 是否允許重載 核心庫支持的運算

說  明

雙括號連接運算符 :=     雙括號連接 冒號前和等號后都必須是括號
單括號連接運算符 ( )=     單括號連接 等號后是一個表達式
[ ]=     單括號連接
{ }=     單括號連接
括號運算符 ( ) 小括號   括號運算 返回最后一個語句的值
[ ] 中括號   括號運算
{ } 大括號   括號運算
命名空間成員訪問符 :: 雙冒號   訪問命名空間成員 訪問命名空間成員
對象成員運算符 .   訪問對象成員或傳遞函數參數 也稱為函數參數運算符,或者變量函數調用運算符
后置單目運算符 ++ 后置自增 整數、實數 后置單目運算符(自增、自減、轉置、點轉置)
-- 后置自減 整數、實數
' 轉置 未定義
.' 點轉置 未定義
前置單目運算符 ! 邏輯值、整數、實數 前置單目運算符(非、正、負、自增、自減、按位非)

對整數或實數求非時,返回邏輯值,且規定!0=true,!0.0=true,其他情況均返回false。

+   被忽略
- 整數、實數、復數、三維向量
++ 前置自增 整數、實數
-- 前置自減 整數、實數
!! 按位非 整數
乘方算術運算符 ^ 乘方 整數、實數、復數 算術運算符(乘方、點乘方)
.^ 點乘方 未定義
乘除算術運算符 * 整數、實數、復數、三維向量 算術運算符(乘、左除、右除、求模、點乘、點左除、點右除)
/ 左除 整數、實數、復數
\ 右除 未定義
% 求模 整數
.* 點乘 未定義
./ 點左除 未定義
.\ 點右除 未定義
加減算術運算符 + 整數、實數、復數、三維向量、字符串 算術運算符(加、減)
- 整數、實數、復數、三維向量
移位運算符 << 左移位 整數 左移位、右移位
>> 右移位 整數
關系運算符 > 大于 整數、實數 關系運算符(大于、大于等于、小于、小于等于、等于、不等于)
>= 大于等于 整數、實數
< 小于 整數、實數
<= 小于等于 整數、實數
== 等于 整數、實數、編譯符#生成的整數
!= 不等于 整數、實數、編譯符#生成的整數
按位與 && 按位與 整數 按位與
按位異或 ~~ 按位異或 整數 按位異或
按位或 || 按位或 整數 按位或
邏輯與 & 邏輯與 邏輯值 邏輯與
邏輯異或 ~ 邏輯異或 邏輯值 邏輯異或
邏輯或 | 邏輯或 邏輯值 邏輯或
$ 整數、實數、復數 并。核心庫并運算的結果為復數或三維向量。
賦值運算符 = 賦值   賦值 賦值運算符
對象賦值運算符 .= 對象賦值   對象賦值 變量函數調用運算符與賦值運算符的結合,一般用于對象賦值
語句分隔符 , 逗號   分隔語句 逗號、冒號、分號運算符
: 冒號   分隔語句
; 分號   分隔語句

表2:Lu數據類型(僅供了解使用 )

類別 基本數據類型 標識符 例子1 例子2 例子3 說 明
靜態類型 nil nil nil     未定義的Lu數據或某個運算失敗的返回值。
表達式(函數)句柄   @fun HFor("fun")   由編譯符@或函數HFor獲得。
64位整數 int 12 0x1A 0x123D 64位整數(范圍從-9223372036854775808~9223372036854775807),既可以是10進制數,也可以是16進制數,但數字中不能包含小數點,也不能用科學記數法表示數字。16進制整數以0x開頭,并用A~F表示10~16。
64位雙精度實數 real 1.2 3. 10.3E8 64位雙精度實數(范圍大致從±1.7E-308~±1.7E+308),含小數點,可以用科學記數法表示數字。
復數 complex 2i 1+2i (2$3) 復數(實部和虛部都是64位雙精度實數),以i結尾的數字,或者由運算符$產生。
三維向量 vector (1$2$3) [1$(2$3)] (2i$3) 三維向量(三個分量都是64位雙精度實數),由運算符$產生。
長精度實數         未啟用。
邏輯值 true / false true false 2>3 邏輯值,只有邏輯真和邏輯假兩個值,關系運算或邏輯運算將返回邏輯值。
特殊常量 all all     由系統定義,直接在腳本中使用,其意義由使用這些常量的函數解釋。
data data    
public public    
private private    
protected protected    
virtual virtual    
row row    
rank rank    
inf / INF inf INF  
-inf / -INF -inf -INF  
nan / NaN nan NaN  
self self    
method method    
靜態字符串   "..." @"..." @"\[22]" 靜態字符串。
靜態64位一維整數數組   intss("...") intss("\&\[10]")   靜態64位一維整數數組。
靜態64位一維實數數組   realss("...") realss("\&\[10]")   靜態64位一維實數數組。
與字符串對應的32位整數   #abc #ab_c   由字符串生成的唯一的32位整數,用于系統擴展設計,用編譯符#獲得。
系統定義動態類型
動態64位實數數組 reals new[reals,5] new[reals,2,5] new[reals,data:2.0,3.6] 動態64位實數數組。可以是多維數組。
動態64位整數數組 ints new[ints,5] new[ints,2,5] new[ints,data:2,3] 動態64位整數數組。可以是多維數組。
動態字符串 string new[string,5] new[string,5,"..."] new[string,"..."] 動態字符串。
動態Lu數據 lu lu[2,3.5,"..."] lu{2,lu[3.5,"..."]} new[lu,5:2,3.5,"..."] 動態Lu表。可以存放任意類型的數據。
外部擴展動態類型 私有動態數據類型 由擴展用戶提供       用戶自定義的私有動態數據類型。
公有動態數據類型 由擴展用戶提供       用戶自定義的公有動態數據類型。

    注:表2中外部擴展動態類型即用戶自定義數據類型。

9 Lu支持自定義數據類型和運算符重載 [返回頁首]

    例如你可以設計自定義的矩陣類型并重載+、-、*、/等運算符使之可用于矩陣的運算。Lu的大多數運算符都允許重載。

    Lu擴展庫LuMath中定義了矩陣類型及相關運算,參考:Lu數值計算擴展動態庫LuMath

10 Lu支持模塊化編譯,支持對私有數據的保護 [返回頁首]

    Lu支持表達式(函數)的模塊化編譯。參考Lu編程指南中的函數LuCom,該函數有一個參數nModule,要求給該表達式指定一個模塊號,模塊號用整數進行標識。如果用模塊加鎖函數LockModule對一個模塊號進行了加鎖,則編譯表達式時必須提供加鎖函數。

    在Lu中,一個模塊由一個或多個表達式組成。模塊用一個整數標識,整數可正可負,只要絕對值相等,就屬于同一個模塊。一般用正整數表示該模塊名。模塊共有兩類,即主模塊(0#模塊)和普通模塊(其他標號的模塊)。

    同一模塊中,模塊號為負的表達式稱私有表達式(私有函數),只能被本模塊的表達式所訪問(即調用),在其他模塊中是不可見的;模塊號為正的表達式稱公有表達式或全局表達式 (全局函數),能被任何一個表達式所訪問。主模塊(0#模塊)中的表達式都是私有表達式。任何一個表達式,既可以訪問本模塊中的表達式,也可以訪問其他模塊中的全局表達式,如果本模塊中的一個私有表達式與其他模塊的一個全局表達式重名,將優先調用本模塊中的私有表達式。

    由以上規定可以看出,主模塊可以訪問本模塊中的表達式,也可以訪問其他模塊中的全局表達式。因此,主模塊常常用在Lu腳本的主程序中。

    很少有腳本會提供模塊化編譯功能,但模塊化編譯的確很有用途,因為一個模塊的私有函數和模塊變量,除非該模塊提供了接口(全局函數),在該模塊之外是無法訪問的。

    實際上,C/C++程序只要獲得了表達式的句柄,就可以使用函數LuCal來執行它,無論該表達式是模塊私有的,還是全局的。故從C/C++程序來看,對自己編譯的Lu表達式,討論私有或者全局并沒有意義。但一個C/C++程序有時并不自己編譯Lu腳本(或者只編譯部分腳本),例如實用程序OpenLu使用擴展庫Mlu編譯Lu腳本,這時它只能獲得Lu腳本系統中的部分函數(全局函數,或者顯示輸出的私有函數)句柄,從而使私有數據得到了有效地保護。

11 Lu使用命名空間避免函數重名 [返回頁首]

    使用命名空間可以有效地避免函數重名問題。Lu中可以用函數Module創建模塊命名空間,命名空間創建后,可以用函數OutFun輸出該模塊的表達式(函數),不管是私有函數還是公有函數,都可以輸出。

      Module("Name":"Name1","Name2",... ...)    //創建模塊命名空間Name,繼承自"Name1","Name2",... ...

      OutFun("fun1","fun2","fun3",... ...)      //輸出模塊命名空間中的表達式"fun1","fun2","fun3",... ...

    模塊命名空間只能創建一次,可以繼承,甚至可以循環繼承,如果確實有必要。模塊命名空間是一棵樹或者是一個連通圖。

    模塊命名空間中輸出的表達式可以用命名空間成員訪問符::調用,如:Name::fun1(...)。如果該命名空間中沒有輸出指定的表達式,而該空間的父空間中輸出了同名表達式,就會調用父空間中的同名表達式。可以連續使用訪問符::直接調用指定父空間(或該父空間的父空間)中的表達式,如:Name1::Name2::Name3::fun1(...)。可以看出,模塊命名空間中的表達式調用規則類似于C++中的虛函數調用規則。

    為了避免二級函數(使用C/C++設計注冊到Lu系統的函數)重名,二級函數也可以采用模塊命名空間中的命名方式,如:Fun2::Set(...),稱二級函數命名空間。是否采用二級函數命名方式,取決于提供二級函數的模塊。

    為了避免常量重名,常量也可以采用函數命名空間中的命名方式,如:ConstName::MyConst,稱常量命名空間。常量命名空間可由程序或庫提供,也可用函數const創建。

12 Lu有很強的擴展性 [返回頁首]

    由于Lu支持自定義數據類型和運算符重載,故Lu有很強的擴展性;由于Lu支持模塊化編譯,支持對私有數據的保護,故Lu在擴展時有很強的安全性。

    在核心庫lu32.dll的支持下,通常通過Lu擴展動態庫對Lu系統進行功能擴展,參考:Lu擴展動態庫。不過你可以使用Lu核心庫的輸出函數自己決定擴展方式。

    由于Lu支持對私有數據的保護,故不同的人使用不同的語言設計的Lu擴展庫會協同工作,而不會相互干擾。

    Lu系統中已經實現的常用Lu擴展庫見表3。

表3:常用Lu擴展庫(僅供了解使用)

Lu 擴 展 庫 簡  介
Lu系統擴展動態庫LuSystem     LuSystem是一個Lu系統擴展動態庫,包含一些增強Lu系統功能的函數、對系統內置類型的擴展以及一些新增數據類型等等。LuSystem不僅是對Lu系統的擴充,更在于演示Lu是極易擴充其功能的腳本,很少有腳本允許用戶能方便地添加像字典、結構、類等高級的數據結構,但Lu允許,而且實現這些很容易,因而,LuSystem也是編程用戶極佳的練手工具。
Lu數值計算擴展動態庫LuMath     LuMath的數值算法是以矩陣為基礎,并進行了運算符重載,具有內存消耗低、執行效率高、代碼簡潔、實用性強的特點。LuMath是熟悉C/C++、Fortran的數學愛好者的極佳的練手工具,任何喜歡LuMath的個人、團隊或商業公司可基于此庫開發商業程序。
Lu數值計算擴展動態庫LuIMSL     IMSL是一個集合數學與統計函數的鏈接庫,擁有許多精準的數學統計算法,它的強大、可靠的數學與統計鏈接庫能夠在執行效率與計算資源間取得極佳的平衡。本庫封裝了IMSL庫的部分實用函數。
Lu參數優化動態庫LuOpt     優化函數具有極強的全局優化能力,也可用于求解非線性方程(組)。
Lu窗口庫LuWin     基于Windows API的窗口庫,包含一些窗口函數,特別是繪制2D3D圖形的函數,多線程動態繪制圖形是LuWin的基本特點。該庫需要模塊化編譯運行庫MLu提供支持。
Lu圖形庫OpenLuGl     基于OpenGL的Lu擴展動態庫,在獨立的線程中動態繪制三維圖形。該庫需要模塊化編譯運行庫MLu提供支持。

13 MLu簡化了Lu腳本的使用 [返回頁首]

    MLu(MLu32.dll)是程序和Lu核心庫之間的一個接口庫,MLu會自動加載Lu核心庫和動態加載多個Lu擴展庫,簡化了Lu系統的使用;MLu可對Lu源程序進行模塊化編譯,能夠編譯運行具有固定格式的源程序(字符串表達式),源程序中可以使用C++風格的注釋。此外,MLu還提供了多個線程互斥地訪問Lu資源的功能;提供了Lu運行監視器,以退出耗時較長的程序;提供在腳本中動態編譯函數的功能;提供錯誤處理函數,實現錯誤(異常)處理的恢復模型等等。

    下例是MLu源代碼的格式(僅作舉例,不理解沒關系):

/**********
 八皇后問題是一個古老而著名的問題,是回溯算法的典型例題。
 該問題是19世紀著名的數學家高斯1850年提出:在8×8格的國際象棋盤上擺放8個皇后,使其不能互相攻擊,即任意兩個皇后都不能處于同一行、同一列或同一斜線上,問有多少種擺法。
 高斯認為有76種方案。1854年在柏林的象棋雜志上不同的作者發表了40種不同的解,后來有人用圖論的方法解出92種結果。
 以下算法是從網上搜來的,該算法沒有最終給出排列組合,僅僅給出有多少種組合,但是算法確實十分奧妙。
***********/

//Lu源程序
init(::sum,upperlim)= sum=0, upperlim=1, SetStackMax(1000);  //執行init函數進行初始化
test(row, ld, rd : pos,p : sum,upperlim)= 
//函數定義
{
    which   
//which是一個選擇計算函數
    {
        row != upperlim,
        {
            pos = {upperlim && [!!(row||ld||rd)]},
            while{ pos,   
//while是循環函數
                p = pos&&(-pos),
                pos = pos -p,
                test[row+p, (ld+p)<<1, (rd+p)>>1]
            }
        },
        sum++
    }
};
main(:tm,n:sum,upperlim)= 
//執行main函數獲得結果
{
    tm=clock(), n=13,
    upperlim=(upperlim<<n)-1,
    test(0,0,0),
    o["Queens=",n,",sum=",sum,",耗時約",[clock()-tm]/1000.0,"秒。\r\n"]
};

    參考:Lu模塊化編譯運行庫MLu

14 Lu提供自動內存管理,也可以手動管理內存 [返回頁首]

    C程序員要自己管理內存的分配和回收,而Python具有垃圾自動回收的機制,Lu的動態內存管理兼有二者的特點:既可以手動回收垃圾,也可以完全依賴于Lu的垃圾自動回收機制。通常,Lu中用類似new的函數生成動態對象,而用類似delete的函數銷毀動態對象,這一點類似于C,用戶可以高效地管理內存;所有用戶沒有銷毀的對象,會由Lu的垃圾收集器管理,并最終會被Lu安全地回收,這一點類似于Python。

    Lu的內存管理特點:(1)與C/C++類似,用戶可立即銷毀一個對象;(2)被用戶忽略的垃圾將被自動回收;(3)任何時候,可手動立即啟動垃圾收集器;(4)垃圾回收是有運行開銷的,但如果用戶有效地管理了內存,垃圾回收器可以一次也不啟動。

15 Lu混合編程中對象操作特點 [返回頁首]

    混合編程的關鍵是參數傳遞。Lu是一種嵌入式腳本,采用自動垃圾回收與手動垃圾回收并存可在混合編程中簡化腳本使用、擴大腳本使用范圍并提高混合編程效率和運行效率。

    設主程序語言為C/C++或delphi等,主程序中有一個對象(或結構等)A,要實現在主程序和Lu腳本中對A的聯合操作。

    首先,要使主程序和Lu都能操作對象A,對象A必須注冊到Lu系統中,可注冊為兩類對象,一種注冊對象可被垃圾收集器回收,另一類注冊對象垃圾收集器無法回收。此外,還要向Lu注冊一些操作對象A的函數。

    有以下多種聯合操作方式:

    (1)注冊為垃圾收集器無法回收的對象,基本特點為:

    主程序可生成對象A并注冊到Lu系統,對象A也可在腳本中由專用函數生成;
    主程序可銷毀對象A,Lu腳本中也可銷毀對象A;
    主程序或腳本中都可一次銷毀對象A的所有實例;
    主程序或Lu腳本用戶沒有銷毀的實例由Lu系統最終回收。

    (2)注冊為垃圾收集器可回收的對象,基本特點為:

    主程序可生成對象A并注冊到Lu系統,對象A也可在腳本中由專用函數生成;
    主程序可銷毀對象A,Lu腳本中也可銷毀對象A,銷毀可以是立即進行的,或者暫存到緩沖池中;
    主程序或腳本中都可一次銷毀對象A的所有實例;
    主程序或Lu腳本用戶沒有銷毀的實例由Lu系統最終回收。

    主程序可按一定規則啟動垃圾收集器回收垃圾對象;
    Lu腳本中可立即啟動垃圾收集器回收垃圾對象;
    主程序可設置垃圾收集器不能啟動,則腳本中的垃圾收集器也無法運行。

    注:Lu垃圾收集器采用標記清除算法。

    (3)多種對象并存時,有些對象注冊為垃圾收集器可回收的對象,有些對象注冊為垃圾收集器不可回收的對象,各自具備各自的特點,不相互影響。

    由于自動垃圾回收與手動垃圾回收并存,故無論在主程序,還是在Lu腳本中銷毀一個對象,不必擔心會帶來任何問題。而只采用自動垃圾回收的腳本系統,在實現復雜功能時,主程序和腳本系統接口上需費很多心思,往往會費力不討好。

16 Lu支持協程 [返回頁首]

    雖然許多腳本支持協程,但Lu腳本協程更簡單,效率更高。

    如果表達式(函數)中使用了函數yield,該表達式稱為一個協程(coroutine)。協程不能遞歸運行,只有這一個限制。Lu協程有4種狀態:正常、運行、掛起、 終止。正常態是可以運行但還沒有運行的狀態;終止態協程是不能運行的,如果運行將返回nil。與協程相關函數有5個:

    yield:掛起協程并立即返回表達式(函數)的值。
    status:查詢表達式(包含協程)的狀態。
    abort:中止掛起的協程,此時協程處于正常態。
    terminate:終止協程,協程處于終止態,不能運行。
    resume:重啟一個終止的協程,協程轉為正常態。

    例子(MLu代碼):

f(x:i)= i=0, while{(i++, i<=5), yield(i)}, 888; //定義了協程f
f[0]; f[0]; f[0]; f[0]; f[0]; f[0]; f[0]; f[0];
//多次調用協程f

    結果(返回888時協程轉為了正常態):

1
2
3
4
5
888
1
2

17 Lu是動態強類型的 [返回頁首]

    Lu是動態強類型的,是指Lu在運行時進行類型檢查(動態),且進行嚴格的類型檢查(強類型)。例如函數f:

f(x,y)=x+y

    執行f(1,2)會得到3,執行f("ab","cd")會得到"abcd",但執行f(1,"cd")會出現運行錯誤(除非定義了整數和字符串相加的運算,否則將出現運行錯誤)。

    由于Lu是強類型的,故Lu腳本中5和5.0是不一樣的,5是一個整數,而5.0是一個實數。所以在Lu中,11/5=2,而11/5.0=2.2(進行了隱式轉換,11被自動轉換為了11.0)。

    Lu的強類型檢查,配合Lu的自定義數據類型和運算符重載,可實現C/C++中的單字節字符類型char,參考使用C/C++給Lu靜態類型數據添加運算符重載功能;也可以實現自定義對象三維向量及相關運算,參考C/C++注冊動態對象到Lu系統并進行運算符重載

18 Lu支持中文編程 [返回頁首]

    Lu使用Unicode字符串作為默認字符串,可很好地實現中文編程。Lu標識符可全部使用中文。

    例子:

兩數加(加數1,加數2)=加數1+加數2;
兩數加(2,3);

19 Lu是可移植的 [返回頁首]

    Lu是由C實現的,故是可移植的,在windows系統中為lu32.dll,在Android系統中為liblu32.so。


版權所有© Lu程序設計 2011-2014,保留所有權利
E-mail: [email protected]
  QQ:630715621
最近更新: 2014年03月25日

福利彩票22选5走势图