最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

淺析C\C++和Lua的通信方式

 更新時間:2014年09月18日 12:04:32   投稿:hebedich  
lua作為小巧精悍的腳本語言,易于嵌入c/c++中 , 廣泛應(yīng)用于游戲AI ,實際上在任何經(jīng)常變化的邏輯上都可以使用lua實現(xiàn),配合c/c++實現(xiàn)的底層接口服務(wù),能夠大大降低系統(tǒng)的維護成本。

為了實現(xiàn)Lua和其他語言之間的通信,Lua虛擬機為C\C++提供了兩個特性:

一,Lua_State狀態(tài)機

       lua_State主要是管理一個lua虛擬機的執(zhí)行環(huán)境, 一個lua虛擬機可以有多個執(zhí)行環(huán)境。Lua虛擬機通過維護這樣一個虛擬棧來實現(xiàn)兩種之間的通信,lua_State定義如下:

struct lua_State {
 CommonHeader;
 lu_byte status;
 StkId top; /* first free slot in the stack */
 global_State *l_G;
 CallInfo *ci; /* call info for current function */
 const Instruction *oldpc; /* last pc traced */
 StkId stack_last; /* last free slot in the stack */
 StkId stack; /* stack base */
 int stacksize;
 unsigned short nny; /* number of non-yieldable calls in stack */
 unsigned short nCcalls; /* number of nested C calls */
 lu_byte hookmask;
 lu_byte allowhook;
 int basehookcount;
 int hookcount;
 lua_Hook hook;
 GCObject *openupval; /* list of open upvalues in this stack */
 GCObject *gclist;
 struct lua_longjmp *errorJmp; /* current error recover point */
 ptrdiff_t errfunc; /* current error handling function (stack index) */
 CallInfo base_ci; /* CallInfo for first level (C calling Lua) */
};

        1,虛擬棧的管理, 包括管理整個棧和當(dāng)前函數(shù)使用的棧的情況

        2,CallInfo的管理, 包括管理整個CallInfo數(shù)組和當(dāng)前函數(shù)的CallInfo

        3,hook相關(guān)的, 包括hookmask, hookcount, hook函數(shù)等

        4,global_State是全局唯一的,存放多個lua_State之間的一些共享數(shù)據(jù)

        5,gc的一些管理和當(dāng)前棧中upvalue的管理

        6,錯誤處理的支持等等

        C\C++和Lua擁有不同的數(shù)據(jù)類型,要實現(xiàn)兩者之間的數(shù)據(jù)通信怎么辦?Lua虛擬機提供Lua_State這樣一種數(shù)據(jù)結(jié)構(gòu)。任何一種數(shù)據(jù)從C\C++傳入Lua虛擬機中,Lua都會將這類數(shù)據(jù)轉(zhuǎn)換為一種通用的結(jié)構(gòu)lua_TValue,并且將數(shù)據(jù)復(fù)制一份,將其壓入虛擬棧中。lua_TValue定義如下:

struct lua_TValue {
 TValuefields;
};
 
#define TValuefields \
  union { struct { Value v__; int tt__; } i; double d__; } u
 
union Value {
 GCObject *gc;  /* collectable objects */
 void *p;     /* light userdata */
 int b;      /* booleans */
 lua_CFunction f; /* light C functions */
 numfield     /* numbers */
};

       Lua有自己的GC,C\C++由自己申請和釋放內(nèi)存,所以兩者之間的內(nèi)存管理是獨立的。從C\C++中傳遞數(shù)據(jù)到Lua虛擬機會發(fā)生數(shù)據(jù)拷貝,從Lua虛擬機中傳遞出來是直接從虛擬棧中取值或者地址,所以數(shù)據(jù)從虛擬棧中pop之后,是否依然是有效引用需要額外注意。

 二,C API

Lua腳本實現(xiàn)交互提供了一系列的C API,常用API有:

        luaL_newstate函數(shù)用于初始化一個lua_State實例

        luaL_openlibs函數(shù)用于打開Lua中的所有標(biāo)準(zhǔn)庫,如io庫、string庫等。

        luaL_loadbuffer編譯了buff中的Lua代碼,如果沒有錯誤,則返回0,同時將編譯后的程序塊壓入虛擬棧中。

        lua_pcall函數(shù)會將程序塊從棧中彈出,并在保護模式下運行該程序塊。執(zhí)行成功返回0,否則將錯誤信息壓入棧中。

        lua_tostring函數(shù)中的-1,表示棧頂?shù)乃饕?,棧底的索引值?,以此類推。該函數(shù)將返回棧頂?shù)腻e誤信息,但是不會將其從棧中彈出。

        lua_pop是一個宏,用于從虛擬棧中彈出指定數(shù)量的元素,這里的1表示僅彈出棧頂?shù)脑亍?/p>

        lua_close用于釋放狀態(tài)指針?biāo)玫馁Y源。

入棧操作:

        Lua針對每種C類型,都有一個C API函數(shù)與之對應(yīng),如:

        void lua_pushnil(lua_State* L);  --nil值

        void lua_pushboolean(lua_State* L, int b); --布爾值

        void lua_pushnumber(lua_State* L, lua_Number n); --浮點數(shù)

        void lua_pushinteger(lua_State* L, lua_Integer n);  --整型

        void lua_pushlstring(lua_State* L, const char* s, size_t len); --指定長度的內(nèi)存數(shù)據(jù)

        void lua_pushstring(lua_State* L, const char* s);  --以零結(jié)尾的字符串,其長度可由strlen得出。

出棧操作:

        API使用“索引”來引用棧中的元素,第一個壓入棧的為1,第二個為2,依此類推。我們也可以使用負數(shù)作為索引值,其中-1表示為棧頂元素,-2為棧頂下面的元素,同樣依此類推。

        Lua提供了一組特定的函數(shù)用于檢查返回元素的類型,如:

        int lua_isboolean (lua_State *L, int index);

        int lua_iscfunction (lua_State *L, int index);

        int lua_isfunction (lua_State *L, int index);

        int lua_isnil (lua_State *L, int index);

        int lua_islightuserdata (lua_State *L, int index);

        int lua_isnumber (lua_State *L, int index);

        int lua_isstring (lua_State *L, int index);

        int lua_istable (lua_State *L, int index);

        int lua_isuserdata (lua_State *L, int index);

        以上函數(shù),成功返回1,否則返回0。需要特別指出的是,對于lua_isnumber而言,不會檢查值是否為數(shù)字類型,而是檢查值是否能轉(zhuǎn)換為數(shù)字類型。

如有任何疑問和建議,歡迎指出討論,謝謝~

相關(guān)文章

  • Lua中的函數(shù)寫法簡明示例

    Lua中的函數(shù)寫法簡明示例

    這篇文章主要介紹了Lua中的函數(shù)寫法簡明示例,本文是一篇個人學(xué)習(xí)筆記,簡單的記錄了Lua函數(shù)的寫法,需要的朋友可以參考下
    2015-04-04
  • Lua下基本的網(wǎng)絡(luò)編程示例

    Lua下基本的網(wǎng)絡(luò)編程示例

    這篇文章主要介紹了Lua下基本的網(wǎng)絡(luò)編程示例,包括簡單的服務(wù)器的搭建和相關(guān)web組件的介紹等,需要的朋友可以參考下
    2015-05-05
  • Lua數(shù)據(jù)類型介紹

    Lua數(shù)據(jù)類型介紹

    這篇文章主要介紹了Lua數(shù)據(jù)類型介紹,本文講解了Lua中的nil(空)、boolean(布爾)、number(數(shù)字)、string(字符串)、table(表)、function(函數(shù))、thread(線程)、userdata(自定義類型)等數(shù)據(jù)類型,需要的朋友可以參考下
    2014-12-12
  • Lua學(xué)習(xí)筆記之運算符和表達式

    Lua學(xué)習(xí)筆記之運算符和表達式

    這篇文章主要介紹了Lua學(xué)習(xí)筆記之運算符和表達式,本文在代碼中使用注釋對Lua的運算符和表達式做了講解,需要的朋友可以參考下
    2014-09-09
  • Lua中的變量類型與語句學(xué)習(xí)總結(jié)

    Lua中的變量類型與語句學(xué)習(xí)總結(jié)

    這篇文章主要介紹了Lua中的變量類型與語句學(xué)習(xí)總結(jié),總結(jié)了Lua入門過程中的一些基礎(chǔ)知識,需要的朋友可以參考下
    2016-06-06
  • Lua中訪問table里函數(shù)的方法示例

    Lua中訪問table里函數(shù)的方法示例

    這篇文章主要介紹了Lua中訪問table里函數(shù)的方法示例,本文例子超級簡單,算是入門實例吧,其實只需要表名.方法名即可訪問,重要的還是其它代碼寫法,本文給出了一個完整的代碼示例,需要的朋友可以參考下
    2015-04-04
  • 安裝Nginx+Lua開發(fā)環(huán)境

    安裝Nginx+Lua開發(fā)環(huán)境

    本文主要詳細介紹了安裝Nginx+Lua開發(fā)環(huán)境的過程以及nginx+lua的配置,十分的詳盡,這里推薦給小伙伴們。
    2015-02-02
  • 獲取Lua表結(jié)構(gòu)(table)數(shù)據(jù)實例

    獲取Lua表結(jié)構(gòu)(table)數(shù)據(jù)實例

    這篇文章主要介紹了獲取Lua表結(jié)構(gòu)(table)數(shù)據(jù)實例,本文使用lua_gettable函數(shù)獲取表結(jié)構(gòu),需要的朋友可以參考下
    2014-09-09
  • Lua中遍歷數(shù)組和table的4種方法

    Lua中遍歷數(shù)組和table的4種方法

    這篇文章主要介紹了Lua中遍歷數(shù)組和table的4種方法,本文講解了使用for遍歷、迭代器的方式遍歷等方法,同時提供一個復(fù)雜table的的遍歷方法,需要的朋友可以參考下
    2015-04-04
  • Lua中的遞歸函數(shù)寫法實例

    Lua中的遞歸函數(shù)寫法實例

    這篇文章主要介紹了Lua中的遞歸函數(shù)寫法實例,本文直接給出代碼實例,并作了簡潔注釋,需要的朋友可以參考下
    2015-04-04

最新評論

海晏县| 合川市| 满洲里市| 丘北县| 天气| 时尚| 杂多县| 饶阳县| 大新县| 福建省| 汉沽区| 安庆市| 资中县| 襄城县| 平昌县| 缙云县| 北宁市| 松桃| 海阳市| 汶上县| 徐州市| 伽师县| 福建省| 卓尼县| 浦江县| 盐亭县| 湛江市| 贵定县| 固安县| 桓台县| 云浮市| 腾冲县| 拉孜县| 酒泉市| 贞丰县| 双流县| 夏邑县| 旬阳县| 广昌县| 旺苍县| 察隅县|