青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

posts - 311, comments - 0, trackbacks - 0, articles - 0
  C++博客 :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理

(搬運工)Lua5.1的常用API

Posted on 2012-07-11 16:43 點點滴滴 閱讀(362) 評論(0)  編輯 收藏 引用 所屬分類: 02 編程語言

lua_State
            Lua狀態機或叫Lua虛擬機,支持多線程,可創建多個狀態機
            typedef int (*lua_Cfunction)(lua_State* L)
            Lua所調用的C函數的函數原型,在C程序中需要將這種函數類型的
            函數注冊到Lua狀態機中,此后Lua才能調用到C的函數
            如果有函數
            int c_Hello(lua_State* l)
            {
               luaL_checktype(l, 1, LUA_TSTRING)
               luaL_checktype(l, 2, LUA_TSTRING)    // 兩個參數都是字符串
                // 先輸出第二個參數,后輸出第一個參數
             printf("%s\t%s\n", lua_tostring(l,-1),lua_tostring(l, -2));
      }

            需在C程序初始化的時候執行以下代碼:
                    // 將函數名壓入LuaVM棧
                    lua_pushstring(l, "c_hello");
                    // 將函數地址壓入LuaVM棧
                    lua_pushcclosure(l, &c_Hello, 0)
                    // 把LuaVM棧上的這個表放入全局表中
                    lua_settable(l, LUA_GLOBALSINDEX)
            此后在Lua中就可以這樣調用:
                    c_hello()

            注:C函數的實現如果有參數的話最好為每一個參數進行類型檢查
                    以確保所棧里的參數是函數參數類型匹配

    lua_State* lua_newstate(lua_Alloc f, void* ud)
            新建一個LuaVM,可以直接調用lua_open來調用這個函數

    void lua_close(lua_State* l))
            關閉LuaVM


    關于棧幀
            當一個函數調用發生的時候就形成了一個棧幀,當這個函數調用結束
            后這個棧幀就消失了

            如在Lua這樣調用c_hello("Hello", "World"),那么c_Hello所看到
            棧幀就是從它的參數開始,如下圖:
            可以有兩種索引方式對棧頂進行操作,正數和負數。    



    棧相關操作
            int (lua_gettop) (lua_State *L)
                    取得當前使用了多少棧空間
            void (lua_settop) (lua_State *L, int idx)
                    把棧頂設置在idx處,相當于做了一次函數調用改變了棧幀
                    如果這個時候調用 lua_settop(L, 1),則會把剛壓入棧的兩個參數刪除
            void (lua_pushvalue) (lua_State *L, int idx)
                    向此棧幀的第idx個位置的值壓入棧頂,相當于復制
            void (lua_remove) (lua_State *L, int idx)
                    刪除第idx個位置的值
                    如果lua_remove(L, -2)則會將"Hello"刪除而剩下"World"在棧頂
                    并會被移到原來"Hello"存放的位置
            void (lua_insert) (lua_State *L, int idx);
                    先將整個上移或下移,并將棧頂的值壓入空出的位置
            void (lua_replace) (lua_State *L, int idx)
                    把棧頂的值替換掉idx處的值
            int (lua_checkstack) (lua_State *L, int sz)
                    檢查棧的大小是否已經增長到最大值,如果沒有則將棧的大小增長sz
                    返回0表示棧溢出,返回1表示成功
            void (lua_xmove) (lua_State *from, lua_State*to, int n)
                    從LavVM的棧頂移動n個值到to的LuaVM的棧頂


    棧存取操作
            以下函數往棧頂壓入一個C值
            void (lua_pushnil) (lua_State *L)
                    往棧頂壓入一個NIL值
            void (lua_pushnumber) (lua_State *L, lua_Number n)
                    往棧頂壓入一個實數
            void (lua_pushinteger) (lua_State *L,lua_Integer n)
                    往棧頂壓入一個整數
            void (lua_pushlstring) (lua_State *L, const char*s, size_t l)
                    往棧頂壓入一個二進制串
            void (lua_pushstring) (lua_State *L, const char*s)
                    往棧頂壓入一個字符串
            const char *(lua_pushvfstring) (lua_State *L,const char *fmt, va_list argp)
                    往棧頂壓入一個格式化串,不過argp是變參
            const char *(lua_pushfstring) (lua_State *L,const char *fmt, ...)
                    往棧頂壓入一個格式化串
            void (lua_pushcclosure) (lua_State *L,lua_CFunction fn, int n)
                    壓入一個函數
            void (lua_pushboolean) (lua_State *L, int b)
                    往棧頂壓入一個bool類型
            void (lua_pushlightuserdata) (lua_State *L, void*p)
                    往棧頂壓入一個數組,數組的內存塊指向p
            int (lua_pushthread) (lua_State *L)


            以下函數往從棧中復制一個值存入棧頂
            void (lua_gettable) (lua_State *L, int idx)
                    idx指向表在棧中的位置,彈出棧頂的key取得表中的值并壓入棧頂
                    此函數與lua_rawget的區別在于此函數會調用metatable的方法
            void (lua_getfield) (lua_State *L, int idx,const char *k)
                    以k所在棧中的索引(idx)作為參數,取得k對應的值并壓入棧頂
                    效率與lua_gettable相同
            void (lua_rawget) (lua_State *L, int idx)
                    idx指向表在棧中的位置,彈出棧頂的key取得表中的值并壓入棧頂
                    為了提高數據訪問的效率而直接讀取表中的數據,不需要對metamethod的調用
                    這個函數在循環訪問數組元素比較方便
            void (lua_rawgeti) (lua_State *L, int idx, intn)
                    idx指向表在棧中的位置,n指向key在棧中的位置,取得表中的值并入棧
                    相當于:lua_pushnumber(L,n);lua_rawget(L,idx)
            void (lua_createtable) (lua_State *L, int narr,int nrec)
                    新建一個表并壓入棧頂,表的大小為narr,并預留了nrec個元素空間
            void *(lua_newuserdata) (lua_State *L, size_t sz)
                    在棧中分配一塊大小為sz的內存并把管理結構入棧且返回內存地址
            int (lua_getmetatable) (lua_State *L, intobjindex)
                    objindex指向對象在棧中的位置,取得對象的metatable并將其壓入棧頂
                    如果失敗或者對象沒有metatable表則返回0
            void (lua_getfenv) (lua_State *L, int idx)
                    idx指向對象所在棧中的位置,取得此對象并將其環境量壓入棧

            以下函數用于判斷棧內某處值的類型
            int (lua_isnumber) (lua_State *L, int idx)
                    棧idx處的值是否是實數
            int (lua_isstring) (lua_State *L, int idx)
                    棧idx處的值是否是字符串
            int (lua_iscfunction) (lua_State *L, int idx)
                    棧idx處的值是否是函數
            int (lua_isuserdata) (lua_State *L, int idx)
                    棧idx處的值是否是二進制數據
            int (lua_type) (lua_State *L, int idx)
                    取得棧idx處的值的類型
            const char *(lua_typename) (lua_State *L, inttp)
                    將類型轉換成C字符串
            int (lua_equal) (lua_State *L, int idx1, intidx2)
                    棧內兩個值是否相等,類型和值都需要相等才返回真
            int (lua_rawequal) (lua_State *L, int idx1, intidx2)
                    棧內兩個對象是否相等,如果是對象時所指對象相同也算相等
            int (lua_lessthan) (lua_State *L, int idx1, intidx2)
                    棧內兩個值的大小,idx1處的值是否小于idx2處的值

            以下函數將棧內的某個格轉換成C能理解的值,棧結構不變
            lua_Number (lua_tonumber) (lua_State *L, intidx)
                    將idx所指向的Lua值轉換成實數返回
            lua_Integer (lua_tointeger) (lua_State *L, intidx)
                    將idx所指向的Lua值轉換成整數返回
            int (lua_toboolean) (lua_State *L, int idx)
                    將idx所指向的Lua值轉換成bool值返回
            const char *(lua_tolstring) (lua_State *L, intidx, size_t *len)
                    將idx所指向的Lua值轉換成字符串返回,并把長度存入len中
            size_t (lua_objlen) (lua_State *L, int idx)
                    取得idx所指向的Lua值長度
            lua_Cfunction (lua_tocfunction) (lua_State *L,int idx)
                    將idx所指向的Lua值轉換成函數返回
            void *(lua_touserdata) (lua_State *L, int idx)
                    將idx所指向的Lua值轉換成內存塊(數組)返回
            lua_State *(lua_tothread) (lua_State *L, intidx)
                    將idx所指向的Lua值轉換成LuaVM對象返回
            const void *(lua_topointer) (lua_State *L, intidx)
                    取得idx所指對象的值的存儲地址返回

            以下函數與其對應的get函數類似
            void (lua_settable) (lua_State *L, int idx)
            void (lua_setfield) (lua_State *L, int idx,const char *k)
            void (lua_rawset) (lua_State *L, int idx)
            void (lua_rawseti) (lua_State *L, int idx, intn)
            int (lua_setmetatable) (lua_State *L, intobjindex)
            int (lua_setfenv) (lua_State *L, int idx)

    函數調用
      關于函數調用
          當需要調用一個Lua函數時,先要將函數壓入棧中,然后將其參數依次壓入
            如下圖:

             假設在Lua代碼中有函數:
                function hello(x, y)
                  print(x, y)
                end
                則在C中可以這樣來調用:
               lua_getglobal(L, "hello"); -- 從全局域中取得hello函數并壓入棧頂
                lua_pushstring(L, "Hello"); -- 依次壓入兩個參數
               lua_pushstring(L, "World");    
                lua_call(L, 2, 0); -- 跳過兩個參數取得函數并調用此函數,函數中會取得相應參數
                                    
            void (lua_call) (lua_State *L, int nargs, intnresults)
                    無保護的函數調用
                    nargs是指調用函數的參數個數,nresults是指所調用的函數的返回值個數
            int (lua_pcall) (lua_State *L, int nargs, intnresults, int errfunc)
                    與lua_call相似,不過此函數是在保護模式下被調用
                    如果發生錯誤則會將錯誤壓入棧,否則功能與lua_call一樣
            int (lua_cpcall) (lua_State *L, lua_CFunction func, void *ud)
                    直接調用一個C函數,并把ud做為func函數調用的參數
                    也就是說在func函數內部看來第一個參數是ud
            int (lua_load) (lua_State *L, lua_Reader reader,void *dt, const char *chunkname);
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            亚洲一区二区三区免费观看| 久久亚洲色图| 狠狠入ady亚洲精品| 99视频精品| 亚洲午夜久久久久久久久电影院 | 欧美亚洲一级片| 欧美激情精品久久久久| 欧美国产一区二区| 亚洲人成免费| 欧美激情视频在线播放| 最新中文字幕一区二区三区| 亚洲国产精品女人久久久| 米奇777在线欧美播放| 亚洲第一精品在线| 亚洲三级性片| 欧美日韩黄色一区二区| 亚洲一区二区不卡免费| 久久精品水蜜桃av综合天堂| 激情久久久久久久| 久久亚洲精品一区| 亚洲福利视频网| 宅男噜噜噜66一区二区66| 欧美性久久久| 亚洲图片激情小说| 欧美一级二级三级蜜桃| 国内精品**久久毛片app| 久久免费的精品国产v∧| 噜噜噜91成人网| 国产综合激情| 噜噜噜91成人网| 亚洲片在线观看| 亚洲影院色在线观看免费| 国产精品福利在线| 欧美一区二区三区视频| 久久久免费精品视频| 亚洲电影自拍| 欧美日本在线视频| 一区二区三区毛片| 亚洲一卡久久| 精品成人国产在线观看男人呻吟| 欧美国产91| 亚洲永久视频| 欧美成人一品| 亚洲欧美日韩另类| 亚洲国产精品va在线观看黑人 | 日韩午夜精品视频| 久久精品麻豆| 99精品热视频只有精品10| 国产精品综合不卡av| 久久深夜福利免费观看| 一区二区三区鲁丝不卡| 欧美成人黑人xx视频免费观看 | 黄色av日韩| 国产精品成人播放| 理论片一区二区在线| 亚洲午夜精品| 亚洲国产精品综合| 久久精品成人| 亚洲午夜久久久| 亚洲黄色毛片| 国产在线一区二区三区四区 | 欧美黄色一区| 性感少妇一区| 日韩视频专区| 欧美大片一区二区| 久久精品人人做人人爽| 在线中文字幕一区| 亚洲国产导航| 国内精品久久久久影院薰衣草| 欧美色视频在线| 欧美激情视频一区二区三区免费| 久久精品视频导航| 亚洲欧洲av一区二区| 日韩午夜在线电影| 亚洲高清视频一区二区| 久久综合激情| 久久av一区二区三区漫画| 亚洲一区二区视频在线观看| 亚洲人成小说网站色在线| 国内成+人亚洲| 国产精品亚洲美女av网站| 欧美视频手机在线| 欧美日韩国产欧美日美国产精品| 开元免费观看欧美电视剧网站| 亚洲欧美日韩一区在线| 亚洲午夜黄色| 亚洲一区免费视频| 亚洲天堂网在线观看| 亚洲视频电影在线| 亚洲久久成人| 亚洲精选久久| 亚洲美女色禁图| 亚洲九九九在线观看| 亚洲精品一区二区在线| 日韩视频免费在线| 日韩一级黄色大片| 亚洲免费大片| 亚洲第一区在线观看| 久久久天天操| 久久久精品一品道一区| 久久成人久久爱| 久久av一区二区三区漫画| 久久国产精品一区二区三区四区| 欧美一区二区三区免费在线看 | 亚洲精品久久久久久久久久久 | 国产一区二区三区黄视频| 国产日韩一区二区三区在线播放| 国产日韩一区在线| 红桃av永久久久| 亚洲国产天堂久久国产91| 亚洲精品看片| 亚洲激情不卡| 欧美在线观看网址综合| 欧美一区二区三区男人的天堂| 久久精品国产第一区二区三区最新章节 | 亚洲精品一区二区三区不| 99在线热播精品免费99热| 中日韩高清电影网| 午夜亚洲一区| 久久久亚洲一区| 欧美成人免费在线| 欧美性理论片在线观看片免费| 国产精品午夜电影| 樱桃视频在线观看一区| 亚洲国产综合在线| 一区二区三区成人| 欧美亚洲网站| 欧美福利精品| 亚洲一区999| 久久中文精品| 国产精品成人一区| 精品成人在线视频| 在线亚洲一区| 久久久99爱| 亚洲国产欧美在线人成| 中日韩高清电影网| 老牛影视一区二区三区| 国产精品国内视频| 曰韩精品一区二区| 亚洲少妇一区| 久久久久免费观看| 亚洲精品一区在线观看香蕉| 欧美中文日韩| 国产精品白丝av嫩草影院| 极品尤物av久久免费看| 中国成人亚色综合网站| 久久精品在线播放| 99国产精品久久| 久久久亚洲综合| 国产伦精品一区二区三区高清版| 最新成人av在线| 欧美一区二区视频97| 亚洲国产人成综合网站| 午夜欧美不卡精品aaaaa| 欧美激情国产日韩精品一区18| 国产日韩欧美在线视频观看| 亚洲美女av网站| 久久国产日韩欧美| 日韩亚洲视频在线| 久久影院午夜论| 国产视频精品免费播放| 一区二区三区回区在观看免费视频 | 国产九九精品视频| 亚洲精品一区久久久久久| 91久久夜色精品国产九色| 另类激情亚洲| 亚洲视频在线二区| 欧美刺激午夜性久久久久久久| 久久精品99国产精品酒店日本| 亚洲深夜av| 亚洲电影网站| 久久男人资源视频| 国产精品自拍一区| 亚洲香蕉网站| 亚洲美女色禁图| 欧美激情一区二区三区成人| 有坂深雪在线一区| 欧美中文字幕视频| 在线视频一区观看| 欧美日韩国产高清| av不卡在线| 亚洲国产三级网| 免费在线欧美黄色| 亚洲黄色性网站| 欧美国产综合一区二区| 久久人人爽人人爽| 在线播放日韩专区| 久久裸体艺术| 欧美在线不卡视频| 黄色成人在线| 欧美 日韩 国产 一区| 久久久久一区二区三区| 黄色一区二区在线| 久久亚洲精品网站| 久久久久国产精品午夜一区| 国产自产v一区二区三区c| 久久久精品日韩| 久久久999成人| 亚洲国产精品传媒在线观看 | 久久久999精品免费|