JavaCPP使用

部分內容引用自網站:https://www.ibm.com/developerworks/cn/java/j-lo-cpp/index.html
GitHub: https://github.com/bytedeco/javacpp
如有侵權請聯繫筆者刪除

JavaCPP是一個開源庫,它提供了在 Java 中高效訪問本地 C++的方法。採用 JNI 技術實現,所以支持所有 Java 實現包括 Android 系統,Avian 和 RoboVM。

爲了調用本地方法,JavaCPP 生成了對應的 JNI 代碼,並且把這些代碼輸入到 C++編譯器,用來構建本地庫。使用了 Annotations 特性的 Java 代碼在運行時會自動調用 Loader.load() 方法從 Java 資源裏載入本地庫,這裏指的資源是工程構建過程中配置好的。

示例:
這是一個簡單的注入/讀出方法,類似於 JavaBean 的工作方式。清單 1 所示的 LegacyLibrary.h 包含了 C++類。

清單 1. LegacyLibrary.h

#include <string>
namespace LegacyLibrary {
 	class LegacyClass {
     public:
 	const std::string& get_property() { return property; }
 	void set_property(const std::string& property) { this->property = property; }
 	std::string property;
 	};
}

接下來定義一個 Java 類,驅動 JavaCPP 來完成調用 C++代碼。

清單 2. LegacyLibrary.java

import org.bytedeco.javacpp.*;
import org.bytedeco.javacpp.annotation.*;
 
@Platform(include="LegacyLibrary.h")
@Namespace("LegacyLibrary")
public class LegacyLibrary {
 	public static class LegacyClass extends Pointer {
 	static { Loader.load(); }
 	public LegacyClass() { allocate(); }
 	private native void allocate();
 
 	// to call the getter and setter functions 
 	public native @StdString String get_property(); public native void set_property(String property);
 
	 // to access the member variable directly
 	public native @StdString String property(); public native void property(String property);
 }
 
 	public static void main(String[] args) {
 	// Pointer objects allocated in Java get deallocated once they become unreachable,
 	// but C++ destructors can still be called in a timely fashion with Pointer.deallocate()
 	LegacyClass l = new LegacyClass();
 	l.set_property("Hello World!");
 	System.out.println(l.property());
 }
}

以上兩個類放在一個目錄下面,接下來運行一系列編譯指令,如清單 3 所示。

清單 3. 運行命令

$ javac -cp javacpp.jar LegacyLibrary.java 
$ java -jar javacpp.jar LegacyLibrary
$ java -cp javacpp.jar LegacyLibrary
Hello World!

我們看到清單 3 最後運行輸出了一行“Hello World!”,這是 LegacyLibrary 類裏面定義好的,通過一個 setter 方法注入字符串,getter 方法讀出字符串。

上述內容都是引用自網站https://www.ibm.com/developerworks/cn/java/j-lo-cpp/index.html

光看別人的東西還是一知半解,所以筆者親自動手試了一下,發現總是生成不了dll文件,在這裏詳細記錄一下,僅供參考。歡迎各位討論

第一步:
參照上述內容創建 Legacylibrary.h LegacyLibrary.java文件並將其和 javacpp.jar 文件放在一個文件夾裏。

第二步:
打開VS的本機命令工具提示窗口(和Windows命令行窗口一樣),用次命令窗口進入到以上三個文件所在的文件夾目錄下,再用

$ javac -cp javacpp.jar LegacyLibrary.java 
$ java -jar javacpp.jar LegacyLibrary
$ java -cp javacpp.jar LegacyLibrary

這三條命令去生成 dll 文件庫。
注意: 此處必須使用VS下的命令行進行操作,筆者此前使用Windows自帶命令行一直沒有成功,在執行第二條命令時會報“找不到指定文件”的錯誤。

VS下的命令行窗口啓動如下圖:
在這裏插入圖片描述
點擊打開文件夾並選擇對應的32位或64位工具。(打開命令行窗口時,若上方出現 Cannot determine the location of the VS Common Tools Folder,則需要在環境變量的 path中設置值:c:\windows\system32)

進入三個文件所在的文件夾及執行第一步編譯操作:
在這裏插入圖片描述
生成 dll 文件:
在這裏插入圖片描述
在這裏插入圖片描述
此時程序所在文件夾會生成一個子文件夾“windows-x86_64”,在此文件夾下會有生成的動態鏈接庫以及相關文件。
在這裏插入圖片描述
執行程序:
在這裏插入圖片描述
生成動態鏈接庫後將文件夾“windows-x86_64”整體粘貼到java項目下的 src 目錄下,並加載 javacpp.jar 包然後運行,顯示成功。
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章