1、调用目的
标准的java类库可能不支持你的程序所需的特性。或许你已经有了一个用其他语言写成的库或程序,而你希望在java程序中使用它。你可能需要用底层语言实现一个小型的时间敏感代码,比如汇编,然后在你的java程序中调用这些功能。
2、库文件存放位置
Java一般有两个常用的path:classpath和java.library.path
- classpath:指向jar包的位置
- java.library.path:非java类包的位置(如dll,so)
在程序中编写System.out.println(System.getProperty("java.library.path")); 运行程序即可获得相应的java.library.path指向的目录,然后拷贝你的libxxx.so到java.library.path指向的某个目录下面。
总结:库文件存放位置
- 放在系统默认路径:java.library.path指定目录下
- 通过配置环境变量(可以配置/etc/profile或/root[对应的用户名]/.bash_profile)指定自己想要存放的目录, 例:export LD_LIBRARY_PATH=.:/opt/active/lib:$LD_LIBRARY_PATH
- 放在程序目录中,之后打在jar包里(具体位置在调用方式处说明)
3、调用方式
3.1、Java自带方式
JDK提供给了用户两个方法用于装载库文件,不论是JNI库文件还是非JNI库文件。一个是System.load(String fileName)方法,另一个是System.loadLibrary(String libname)方法,在任何本地方法被调用之前必须先用这两个方法之一把相应的JNI库文件装载。
- System.load(带文件后缀名)
System.load参数必须为库文件的绝对路径,可以是任意路径,例如:
System.load("C:\\Documents and Settings\\TestJNI.dll"); //Windows
System.load("/usr/lib/TestJNI.so"); //Linux
- System.loadLibrary (不带文件后缀名)
System.loadLibrary 参数为库文件名,不包含库文件的扩展名,例如:
System.loadLibrary ("TestJNI"); //加载Windows下的TestJNI.dll本地库
System.loadLibrary ("TestJNI"); //加载Linux下的libTestJNI.so本地库
注意:TestJNI.dll 或 libTestJNI.so 必须是在JVM属性java.library.path所指向的路径中
3.2、JNA方式
JNA(Java Native Access )提供一组Java工具类用于在运行期间动态访问系统本地库(native library:如Window的dll)而不需要编写任何Native/JNI代码。开发人员只要在一个java接口中描述目标native library的函数与结构,JNA将自动实现Java接口到native function的映射。
使用前注意引入JNA所需的jar包
- 可以放在java.library.path中通过Native.loadLibrary("NLPIR", CLibrary.class)直接调用。
- Native.loadLibrary("NLPIR", CLibrary.class)会自动去项目的src/main/resources文件夹下寻找系统对应的dll和so。 (根据com.sun.jna.Platform类对应文件夹名)
- 也可以将库文件放在src目录下,通过Native.loadLibrary("/libNLPIR.so", CLibrary.class)引用,此处需要写全名。
- 当然也可以将库文件放在程序打的jar包的相同目录,应该也可以放在别的目录下,可自行探索
3.3、注意
Linux下:一定要将Linux下的共享库命名成libxxx.so的形式,"xxx"是你在System.loadLibrary("xxx")或Native.loadLibrary("xxx", CLibrary.class)中用到的加载库名称。
Windows下:一定要将Windows下的共享库命名成xxx.dll的形式(没有前边的lib三个字母),"xxx"是你在System.loadLibrary("xxx")或Native.loadLibrary("xxx", CLibrary.class)中用到的加载库名称。