色哟哟视频在线观看-色哟哟视频在线-色哟哟欧美15最新在线-色哟哟免费在线观看-国产l精品国产亚洲区在线观看-国产l精品国产亚洲区久久

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

Java與lua互相調(diào)用簡(jiǎn)單教程

倩倩 ? 來(lái)源:芋道源碼 ? 作者:芋道源碼 ? 2022-09-07 10:47 ? 次閱讀

在某些業(yè)務(wù)場(chǎng)景下,我們可能會(huì)遇到 lua 中要調(diào)用 java 代碼情況,當(dāng)然這個(gè)用 JNI 肯定是可以做到的,但是有更加方便的辦法:LuaJavaBridge(LuaJava)和 LuaJ。

luaj 主要特征

  • 可以從 Lua 調(diào)用 Java Class Static Method
  • 調(diào)用 Java 方法時(shí),支持 int/float/boolean/String/Lua function 五種參數(shù)類型
  • 可以將 Lua function 作為參數(shù)傳遞給 Java,并讓 Java 保存 Lua function 的引用
  • 可以從 Java 調(diào)用 Lua 的全局函數(shù),或者調(diào)用引用指向的 Lua function

luaj 的功能很簡(jiǎn)單,但對(duì)于集成各種 SDK 來(lái)說(shuō)已經(jīng)完全滿足需求了。

基于 Spring Boot + MyBatis Plus + Vue & Element 實(shí)現(xiàn)的后臺(tái)管理系統(tǒng) + 用戶小程序,支持 RBAC 動(dòng)態(tài)權(quán)限、多租戶、數(shù)據(jù)權(quán)限、工作流、三方登錄、支付、短信、商城等功能

  • 項(xiàng)目地址:https://gitee.com/zhijiantianya/ruoyi-vue-pro
  • 視頻教程:https://doc.iocoder.cn/video/

luaj 用法示例

Java 方法原型:

publicstaticfloatgetNum(floatn){
returnn;
}

lua 調(diào)用示例:

--Java類的名稱
localclassName="com/xttblog/Test"
--調(diào)用的Java方法名
localmethod='getNum'
--調(diào)用Java方法需要的參數(shù)
localn=10
localargs={
n
}
--調(diào)用Java方法
local_,testStaticMethod=luaj.callStaticMethod(className,method,args)

基于 Spring Cloud Alibaba + Gateway + Nacos + RocketMQ + Vue & Element 實(shí)現(xiàn)的后臺(tái)管理系統(tǒng) + 用戶小程序,支持 RBAC 動(dòng)態(tài)權(quán)限、多租戶、數(shù)據(jù)權(quán)限、工作流、三方登錄、支付、短信、商城等功能

  • 項(xiàng)目地址:https://gitee.com/zhijiantianya/yudao-cloud
  • 視頻教程:https://doc.iocoder.cn/video/

luaj 實(shí)現(xiàn)原理

luaj 的核心目標(biāo)有兩個(gè):從 Lua 調(diào)用 Java, 從 Java 調(diào)用 Lua。整理出來(lái)就是如下幾點(diǎn)

  • 查找并調(diào)用指定的 Java 方法
  • 檢查調(diào)用結(jié)果,并從 Java 方法獲取返回值
  • 將 Lua function 作為參數(shù)傳遞給 Java 方法
  • 在 Java 方法中調(diào)用 Lua function

查找并調(diào)用指定的 Java 方法

JNI 提供了 FindClass() 方法用于查找指定的 Class,所以 luaj.callStaticMethod() 的第一個(gè)參數(shù)就是要調(diào)用的 Java Class 的完整類名稱(類名稱中的“.”要替換為“/”)

找到指定 Class 后,利用 JNI 的 GetStaticMethodID() 方法就可以找到這個(gè)類的指定靜態(tài)方法,前提是要提供靜態(tài)方法的名稱和簽名。

所謂簽名,就是指Java方法的參數(shù)類型和返回類型定義。方法的簽名就是類似(Ljava/lang/String;ZZI)V這樣的一串描述,通過字節(jié)碼方式可以查看,如下示例:

34c3e5bc-2e57-11ed-ba43-dac502259ad0.png

關(guān)于 Java 方法簽名的具體定義,可以參考:JNI Type Signatures

這里要說(shuō)的是 luaj 可以根據(jù)調(diào)用參數(shù)自動(dòng)猜測(cè)方法簽名所以示例中我們并沒有寫簽名。

示例中指定參數(shù):

localargs={n}

luaj 根據(jù)這 個(gè)參數(shù),會(huì)構(gòu)造出正確的方法簽名。

注意:這里要說(shuō)的是 Lua 里沒有辦法準(zhǔn)確判斷一個(gè)數(shù)值是整數(shù)還是浮點(diǎn)數(shù),所以 luaj 在猜測(cè)方法簽名時(shí),假定所有的數(shù)值都是浮點(diǎn)數(shù)。所以下面調(diào)用會(huì)報(bào)錯(cuò):

publicstaticintgetNum(intn){
returnn;
}

--Java類的名稱
localclassName="com/xttblog/Test"
--調(diào)用的Java方法名
localmethod='getNum'
--調(diào)用Java方法需要的參數(shù)
localn=10
localargs={
n
}
--調(diào)用Java方法
local_,testStaticMethod=luaj.callStaticMethod(className,method,args)

這樣是不行的,所以這個(gè)時(shí)候我們要自己定義簽名。

下面給出正確的示例

publicstaticintgetNum(intn){
returnn;
}
--Java類的名稱
localclassName="com/xttblog/Test"
--調(diào)用的Java方法名
localmethod='getNum'
--調(diào)用Java方法需要的參數(shù)
localn=10
localargs={
n
}
--定義簽名--參數(shù):[I]nteger--返回值:[I]nt
localsig="(I)I"
--調(diào)用Java方法
local_,testStaticMethod=luaj.callStaticMethod(className,method,args,sig)

簽名使用“(依次排列的參數(shù)類型)返回值類型”的格式,幾個(gè)例子如下:

簽名解釋
()V 參數(shù):無(wú),返回值:無(wú)
(I)V 參數(shù):int,返回值:無(wú)
(Ljava/lang/String;)Z 參數(shù):字符串,返回值:布爾值
(IF)Ljava/lang/String;參數(shù):整數(shù)、浮點(diǎn)數(shù),返回值:字符串

這里列出不同類型對(duì)應(yīng)的 Java 簽名字符串:

類型名類型
I整數(shù),或者Luafunction
F浮點(diǎn)數(shù)
Z布爾值
Ljava/lang/String;字符串
VVoid空,僅用于指定一個(gè)Java方法不返回任何值

Java 方法里接收 Lua function 的參數(shù)必須定義為 int 類型

從 Java 方法獲取返回值

luaj 會(huì)檢查調(diào)用結(jié)果,并從 Java 方法獲取返回值。

luaj 調(diào)用 Java 方法時(shí),可能會(huì)出現(xiàn)各種錯(cuò)誤,因此 luaj 提供了一種機(jī)制讓 Lua 調(diào)用代碼可以確定 Java 方法是否成功調(diào)用。

luaj.callStaticMethod()會(huì)返回兩個(gè)值:

  • 當(dāng)成功時(shí),第一個(gè)值為 true,第二個(gè)值是 Java 方法的返回值(如果有)。
  • 當(dāng)失敗時(shí),第一個(gè)值為 false,第二個(gè)值是錯(cuò)誤代碼。

下面的代碼展示了如何檢查返回結(jié)果和獲得返回值:

publicstaticintAddTwoNumbers(finalintnumber1,finalintnumber2){
returnnumber1+number2;
}

Lua代碼

localargs={2,3}
localsig="(II)I"
localok,ret=luaj.callStaticMethod(className,"AddTwoNumbers",args,sig)

ifnotokthen
print("luajerror:",ret)
else
print("ret:",ret)--輸出ret:5
end

錯(cuò)誤代碼定義如下:

錯(cuò)誤代碼描述
-1不支持的參數(shù)類型或返回值類型
-2無(wú)效的簽名
-3沒有找到指定的方法
-4Java方法執(zhí)行時(shí)拋出了異常
-5Java虛擬機(jī)出錯(cuò)
-6Java虛擬機(jī)出錯(cuò)

將 Lua function 作為參數(shù)傳遞給 Java 方法

Lua 虛擬機(jī)中,Lua function 以值的形式保存。但這個(gè)值無(wú)法直接給 Java 用,所以 luaj 做了一個(gè) Lua function 引用表。當(dāng)一個(gè) Lua function 傳遞給 Java 時(shí),這個(gè) function 對(duì)應(yīng)的值會(huì)被存在引用表中,并獲得一個(gè)唯一的引用 ID (整數(shù))。Java 代碼拿到這個(gè)引用 ID 后,就可以很方便的調(diào)用該 Lua function 了。

所以 Java 方法里接收 Lua function 的參數(shù)必須定義為 int 類型。

示例:

publicstaticintgetNum(intn){
returnn;
}

localfunctioncallback(result)
---方法內(nèi)容
end
--Java類的名稱
localclassName="com/xttblog/Test"
--調(diào)用的Java方法名
localmethod='getNum'
--調(diào)用Java方法需要的參數(shù)
localargs={
callback
}
--定義簽名--參數(shù):[I]nteger--返回值:[I]nt
localsig="(I)I"
--調(diào)用Java方法
local_,testStaticMethod=luaj.callStaticMethod(className,method,args,sig)

另外,LuaJ 也很好用。只需引入 pom。

34ff6182-2e57-11ed-ba43-dac502259ad0.png

?然后直接把 lua 代碼當(dāng)做 String 字符串內(nèi)嵌到 Java 代碼中:

StringluaStr="print'hello,world!'";
Globalsglobals=JsePlatform.standardGlobals();
LuaValuechunk=globals.load(luaStr);
chunk.call();

也可以創(chuàng)建一個(gè) login.lua 腳本,內(nèi)容如下:

--無(wú)參函數(shù)
functionhello()
print'hello'
end
--帶參函數(shù)
functiontest(str)
print('datafromjavais:'..str)
return'haha'
end

然后,Java先載入login.lua腳本并編譯,然后再獲取指定名稱的函數(shù),無(wú)參的直接使用call()方法調(diào)用,帶參的需要通過invoke(LuaValue[])傳入?yún)?shù)表:

StringluaPath="res/lua/login.lua";//lua腳本文件所在路徑
Globalsglobals=JsePlatform.standardGlobals();
//加載腳本文件login.lua,并編譯
globals.loadfile(luaPath).call();
//獲取無(wú)參函數(shù)hello
LuaValuefunc=globals.get(LuaValue.valueOf("hello"));
//執(zhí)行hello方法
func.call();
//獲取帶參函數(shù)test
LuaValuefunc1=globals.get(LuaValue.valueOf("test"));
//執(zhí)行test方法,傳入String類型的參數(shù)參數(shù)
Stringdata=func1.call(LuaValue.valueOf("I'amfromJava!")).toString();
//打印lua函數(shù)回傳的數(shù)據(jù)
Logger.info("datareturnfromluais:"+data);

運(yùn)行結(jié)果如下:

hello
datafromjavais:I'amfromJava!
八月07,2022525下午com.tw.login.tools.Loggerinfo
信息: lua return data:haha
350b36b0-2e57-11ed-ba43-dac502259ad0.png

審核編輯 :李倩


聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • JAVA
    +關(guān)注

    關(guān)注

    19

    文章

    2972

    瀏覽量

    104869
  • 函數(shù)
    +關(guān)注

    關(guān)注

    3

    文章

    4338

    瀏覽量

    62769
  • 代碼
    +關(guān)注

    關(guān)注

    30

    文章

    4803

    瀏覽量

    68756

原文標(biāo)題:Java與lua互相調(diào)用簡(jiǎn)單教程

文章出處:【微信號(hào):芋道源碼,微信公眾號(hào):芋道源碼】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。

收藏 人收藏

    評(píng)論

    相關(guān)推薦

    LabVIEW如何調(diào)用Java程序的問題

    本帖最后由 chaosid 于 2013-10-19 02:23 編輯 LabVIEW的互連接口面板中有.NET的函數(shù)調(diào)用節(jié)點(diǎn),但如何調(diào)用Java程序類庫(kù)呢?真誠(chéng)求教各位高手,有思路也行,有
    發(fā)表于 10-19 02:19

    Lua腳本簡(jiǎn)單介紹

    Lua簡(jiǎn)單介紹Lua[1]是一個(gè)小巧的腳本語(yǔ)言。作者是巴西人。該語(yǔ)言的設(shè)計(jì)目的是為了嵌入應(yīng)用程序中,從而為應(yīng)用程序提供靈活的擴(kuò)展和定制功能。Lua腳本能夠非常easy的被C/C++ 代
    發(fā)表于 08-20 06:37

    Lua腳本簡(jiǎn)單介紹

    Lua簡(jiǎn)單介紹Lua[1]是一個(gè)小巧的腳本語(yǔ)言。作者是巴西人。該語(yǔ)言的設(shè)計(jì)目的是為了嵌入應(yīng)用程序中,從而為應(yīng)用程序提供靈活的擴(kuò)展和定制功能。Lua腳本能夠非常easy的被C/C++ 代
    發(fā)表于 08-20 08:06

    Lua簡(jiǎn)單介紹

    Lua簡(jiǎn)單介紹Lua[1]是一個(gè)小巧的腳本語(yǔ)言。作者是巴西人。該語(yǔ)言的設(shè)計(jì)目的是為了嵌入應(yīng)用程序中,從而為應(yīng)用程序提供靈活的擴(kuò)展和定制功能。Lua腳本能夠非常easy的被C/C++代碼
    發(fā)表于 08-20 07:47

    如何用java映射創(chuàng)建java對(duì)象和調(diào)用java對(duì)象呢

    java是一種解析語(yǔ)言,java程序是通過java虛擬機(jī)解析.class的方式運(yùn)行起來(lái)。因此,java中就存在java映射的概念。下面介紹如
    發(fā)表于 04-11 14:43

    如何用java映射創(chuàng)建java對(duì)象和調(diào)用java對(duì)象的方法

    java是一種解析語(yǔ)言,java程序是通過java虛擬機(jī)解析.class的方式運(yùn)行起來(lái)。因此,java中就存在java映射的概念。一、首先我
    發(fā)表于 07-28 16:11

    EPS8266和Lua遇到PANIC:調(diào)用Lua API時(shí)出現(xiàn)未受保護(hù)的錯(cuò)誤...”是怎么回事?

    ) 我收到一個(gè)錯(cuò)誤:“PANIC:調(diào)用 Lua API 時(shí)出現(xiàn)未受保護(hù)的錯(cuò)誤...” 文檔說(shuō)調(diào)用 stop 時(shí) tmr 仍處于注冊(cè)狀態(tài)。 調(diào)用 tmr.state(0) 也是一樣的。
    發(fā)表于 04-27 06:18

    Programming in Lua 3ed

    Lua語(yǔ)言的編程學(xué)習(xí)手冊(cè)。Lua是一個(gè)小巧的腳本語(yǔ)言。Lua腳本可以很容易的被C/C++ 代碼調(diào)用,也可以反過來(lái)調(diào)用C/C++的函數(shù),這使得
    發(fā)表于 10-26 17:21 ?11次下載

    Java調(diào)用window的matlab遇到的問題和解決方案

    Java調(diào)用window的matlab遇到的問題和解決方案
    的頭像 發(fā)表于 06-20 09:32 ?3360次閱讀
    <b class='flag-5'>Java</b>:<b class='flag-5'>調(diào)用</b>window的matlab遇到的問題和解決方案

    調(diào)用Lua新建的WEB服務(wù)器 操作Nodemcu esp8266 控制繼電器實(shí)現(xiàn)物聯(lián)網(wǎng)

    調(diào)用Lua新建的WEB服務(wù)器 操作Nodemcu esp8266 控制繼電器實(shí)現(xiàn)物聯(lián)網(wǎng)
    發(fā)表于 12-08 16:51 ?13次下載
    <b class='flag-5'>調(diào)用</b><b class='flag-5'>Lua</b>新建的WEB服務(wù)器  操作Nodemcu esp8266 控制繼電器實(shí)現(xiàn)物聯(lián)網(wǎng)

    Java方法中調(diào)用Lua function

    Java先載入login.lua腳本并編譯,然后再獲取指定名稱的函數(shù),無(wú)參的直接使用call()方法調(diào)用,帶參的需要通過invoke(LuaValue[])傳入?yún)?shù)表。
    的頭像 發(fā)表于 09-07 10:47 ?1425次閱讀

    微服務(wù)架構(gòu)中的服務(wù)之間如何互相調(diào)用呢?

    在微服務(wù)架構(gòu)中,需要調(diào)用很多服務(wù)才能完成一項(xiàng)功能。服務(wù)之間如何互相調(diào)用就變成微服務(wù)架構(gòu)中的一個(gè)關(guān)鍵問題。
    的頭像 發(fā)表于 01-31 09:46 ?2231次閱讀

    java上位機(jī)開發(fā)(c庫(kù)調(diào)用)

    所有的動(dòng)態(tài)語(yǔ)言,包括在java在內(nèi),一般都會(huì)提供一個(gè)調(diào)用c庫(kù)的方法。java語(yǔ)言的出現(xiàn)是在上個(gè)世紀(jì)90年代,而c/c++出現(xiàn)的時(shí)間要更早 一點(diǎn),大約提前了20多年,所以在這過程當(dāng)中積累了很多的資源
    發(fā)表于 05-09 10:00 ?0次下載
    <b class='flag-5'>java</b>上位機(jī)開發(fā)(c庫(kù)<b class='flag-5'>調(diào)用</b>)

    如何用Rust通過JNI和Java進(jìn)行交互

    近期工作中有Rust和Java互相調(diào)用需求,這篇文章主要介紹如何用Rust通過JNI和Java進(jìn)行交互,還有記錄一下開發(fā)過程中遇到的一些坑。
    的頭像 發(fā)表于 10-17 11:41 ?803次閱讀

    shell調(diào)用java并返回執(zhí)行結(jié)果

    在Shell腳本中調(diào)用Java程序并獲取執(zhí)行結(jié)果,可以通過以下步驟實(shí)現(xiàn): 編寫Java程序:首先,你需要編寫一個(gè)Java程序,包含你想要執(zhí)行的功能。確保你的
    的頭像 發(fā)表于 11-08 10:32 ?1775次閱讀
    主站蜘蛛池模板: 天堂网久久| 凹凸精品视频分类视频| 一线高清视频在线播放| 92国产精品午夜免费福利视频| 拔萝卜视频免费看高清| 国产精品一区二区三区四区五区 | 曰本熟妇乱妇色A片在线| 青青草在现线免费观看| 我把寡妇日出水好爽| 欲香欲色天天综合和网| 达达兔欧美午夜国产亚洲| 好硬好湿好大再深一点动态图| 免费三级网址| 亚洲国产精品免费线观看视频| 亚洲精品成人无码A片在线| 2019久久这里只精品热在线观看| 俄罗斯女人Z0ZOZO| 国产精品XXXXX免费A片| 久久伊人天堂视频网| 色柚视频网站ww色| 中文字幕本庄优花喂奶| 国产AV亚洲精品久久久久软件| 久久久无码精品亚洲欧美| 试看做受120秒免费午夜剧场| 亚洲va精品中文字幕| 99在线免费视频| 狠狠色丁香婷婷久久综合| 日本aaaa| 无码天堂亚洲国产AV久久| 51精品国产AV无码久久久密桃| 99爱在线精品视频网站| 超级碰碰青草久热国产| 久久国内精品视频| 欧美性狂猛AAAAAA| 夜夜躁日日躁狠狠| 国产成人精品综合在线| 年轻漂亮的妺妺中文字幕版| 亚洲欧美日韩高清专区| 俄罗斯人与动ZOZ0| 嗯啊不要老师| 在线欧美精品一区二区三区|