閱讀251 返回首頁    go 阿裏雲 go 技術社區[雲棲]


lua與C(一):C調用lua

      lua和c有兩種關係:

      一種是在lua中調用C的函數,C稱為庫代碼,一種是C中調用lua,C就稱為應用程序代碼,此時C中包含了lua的解釋器

   C代碼部分

       注意在C++中,通常要把lua的一些頭文件定義在extern “c”中,因為他們是C語言實現的。

    1.  作為應用程序調用lua代碼:

char* buffer="print(\"hello,lua\")";
 lua_State* ls=luaL_newstate();
 int error;
 luaL_openlibs(ls);
 error=luaL_loadbuffer(ls,buffer,strlen(buffer),"line");
 printError(ls,error,"loaderror");
 error=lua_pcall(ls,0,0,0);
 printError(ls,error,"callerror");

 error=luaL_loadfile(ls,"1.lua");
 printError(ls,error,"loaderror");
 error=lua_pcall(ls,0,0,0);
 printError(ls,error,"callerror");

 lua_close(ls);
 getchar();
 return ;

所有lua相關的東西都保存在lua_State這個結構中,luaL_loadbuffer=luaL_loadfile加載lua代碼,

lua_pcall安全的執行lua代碼,他將lua代碼在保護模式下運行,不會導致程序的crash,如果想保護與lua交互的c代碼,則可以使用lua_cpcall,他接受的是一個c函數

     與lua代碼間訪問交換數據

      c和lua之間采用棧的方式交換數據。兩邊代碼可以使用各種API將數據壓入到一個公用的棧中,或者利用api從這個棧中取出數據。而事實是幾乎所有的api函數都會使用這個棧。棧的空間是有限的,至少有20個。如果c代碼作為一個庫函數被lua調用,在可能出錯的地方要調用lua_error,來保證在lua中執行時的安全。

另外這個棧不是一個全局的概念,每個函數都有自己的局部私有棧,當lua調用一個c函數時,第一個參數總是這個局部棧的索引1

    2 壓入C元素到棧

    void pushnil/boolean/number/integer/string/lstring/...這些函數壓入不同類型的數據到棧

   壓入一個空表

 lua_newtable

   設置棧中table的值:

   1.先壓入索引key

  2.壓入value

  3.調用lua_settable(Lua_state,index),設置index處的表的[key]=value,注意這個函數結束會彈出key和value

 

   3壓入lua元素到棧

  lua_getglobal()將lua中的某個全局變量壓入棧中

  4 從棧中獲取lua元素

   int lua_toboolean(luaState *L,int index) 等函數

   棧的檢索index正數開始代表從棧地開始的順序,負數代表從棧頂的順序

   可以先使用 lua_is*函數檢測這個元素是不是所要類型或lua_type直接得到他的類型

  獲取table元素:

  1.將元素的key壓入到棧中 lua_pushstring

  2.使用lua_gettable(Lua_state,index)這裏index是table的索引,這個函數可以獲取這個table的索引為key的值,注意這個函數結束會彈出key並將value放於棧頂

 *對於字符串索引,可以用lua_getfield(Lua_state,index,key)來直接獲取

 5從棧中獲取元素設置給lua變量

lua_setglobal("L",name) 將棧頂元素給lua的name變量 ,然後彈出棧

其他棧操作

  lua_gettop得到棧中棧頂的位置,也就是數據的數量 lua_settop設置棧頂元素此外還有insert remove等在棧中間操作的各種操作

 

  7調用lua函數

  1.壓入lua函數到棧lua_getglobal

  2.按參數從左到右順序將c變量作為參數壓入棧

 3.使用lua_pcall調用lua_pcall(Lua_state,參數個數,返回值個數,錯誤處理函數索引),然後參數和函數被彈出,結果被先後壓入棧

如果出錯,lua_pcall將返回一個非零值,然後壓入一條錯誤消息到棧

 

 

 

 

 

 

  

     

 

 

 

  

最後更新:2017-04-02 16:48:08

  上一篇:go iOS中注冊功能的體驗探究
  下一篇:go MVC ViewData和ViewBag