java代码编译so,Java代码编译过之后还可以重复编译吗

java jni 怎么在windows环境中编译成linux下的so文件

可以直接在android工程下使用,因为android就是linux内核。

创新互联的客户来自各行各业,为了共同目标,我们在工作上密切配合,从创业型小企业到企事业单位,感谢他们对我们的要求,感谢他们从不同领域给我们带来的挑战,让我们激情的团队有机会用头脑与智慧不断的给客户带来惊喜。专业领域包括网站设计、网站建设、电商网站开发、微信营销、系统平台开发。

android的NDK开发需要在linux下进行: 因为需要把C/C++编写的代码生成能在arm上运行的.so文件,这就需要用到交叉编译环境,而交叉编译需要在linux系统下才能完成。

2.安装android-ndk开发包,这个开发包可以在google android : 通过这个开发包的工具才能将android jni 的C/C++的代码编译成库

3.android应用程序开发环境: 包括eclipse、java、 android sdk、 adt等。

NDK编译步骤:

选择 ndk 自带的例子 hello-jni ,位于E:\android-ndk-r5\samples\hello-jni( 根据具体的安装位置而定 ) 。

2.运行 cygwin ,输入命令 cd /cygdrive/e/android-ndk-r5/samples/hello-jni ,进入到 E:\android-ndk-r5\samples\hello-jni 目录。

3.输入 $NDK/ndk-build ,执行成功后,它会自动生成一个 libs 目录,把编译生成的 .so 文件放在里面。 ($NDK是调用我们之前配置好的环境变量, ndk-build 是调用 ndk 的编译程序 )

4.此时去 hello-jni 的 libs 目录下看有没有生成的 .so 文件,如果有,ndk 就运行正常啦。

如何把JAVA工程 编译成.SO文件

1,写一个java文件,声明一个native 方法,例如public native void test(); 2,把它编译成class文件 3,使用javah 这个class来生成cpp的头文件 4,实现头文件里面那些函数 4,用ndk编译生成动态库 其中1,想生成几个就写几个native方法。

java 调用so文件

用JNI实现

实例:

创建HelloWorld.java

class HelloWorld

{

private native void print();

public staticvoid main(String[] args)

{

new HelloWorld().print();

}

static

{

System.loadLibrary("HelloWorld");

}

}

注意print方法的声明,关键字native表明该方法是一个原生代码实现的。另外注意static代码段的System.loadLibrary调用,这段代码表示在程序加载的时候,自动加载libHelloWorld.so库。

编译HelloWorld.java

在命令行中运行如下命令:

javac HelloWorld.java

在当前文件夹编译生成HelloWorld.class。

生成HelloWorld.h

在命令行中运行如下命令:

javah -jni HelloWorld

在当前文件夹中会生成HelloWorld.h。打开HelloWorld.h将会发现如下代码:

/* DO NOT EDIT THIS FILE - it is machine generated */

#include jni.h

/* Header for class HelloWorld */

#ifndef _Included_HelloWorld

#define _Included_HelloWorld

#ifdef __cplusplus

extern "C" {

#endif

/*

* Class: HelloWorld

* Method: print

* Signature: ()V

*/

JNIEXPORT void JNICALL Java_HelloWorld_print

(JNIEnv *, jobject);

#ifdef __cplusplus

}

#endif

#endif

该文件中包含了一个函数Java_HelloWorld_print的声明。这里面包含两个参数,非常重要,后面讲实现的时候会讲到。

实现HelloWorld.c

创建HelloWorld.c文件输入如下的代码:

#include jni.h

#include stdio.h

#include "HelloWorld.h"

JNIEXPORT void JNICALL

Java_HelloWorld_print(JNIEnv *env, jobject obj)

{

printf("Hello World!\n");

}

注意必须要包含jni.h头文件,该文件中定义了JNI用到的各种类型,宏定义等。

另外需要注意Java_HelloWorld_print的两个参数,本例比较简单,不需要用到这两个参数。但是这两个参数在JNI中非常重要。

env代表java虚拟机环境,Java传过来的参数和c有很大的不同,需要调用JVM提供的接口来转换成C类型的,就是通过调用env方法来完成转换的。

obj代表调用的对象,相当于c++的this。当c函数需要改变调用对象成员变量时,可以通过操作这个对象来完成。

编译生成libHelloWorld.so

在Linux下执行如下命令来完成编译工作:

cc -I/usr/lib/jvm/java-6-sun/include/linux/

-I/usr/lib/jvm/java-6-sun/include/

-fPIC -shared -o libHelloWorld.so HelloWorld.c

在当前目录生成libHelloWorld.so。注意一定需要包含Java的include目录(请根据自己系统环境设定),因为Helloworld.c中包含了jni.h。

另外一个值得注意的是在HelloWorld.java中我们LoadLibrary方法加载的是

“HelloWorld”,可我们生成的Library却是libHelloWorld。这是Linux的链接规定的,一个库的必须要是:lib+库

名+.so。链接的时候只需要提供库名就可以了。

运行Java程序HelloWorld

大功告成最后一步,验证前面的成果的时刻到了:

java HelloWorld

如果你这步发生问题,如果这步你收到java.lang.UnsatisfiedLinkError异常,可以通过如下方式指明共享库的路径:

java -Djava.library.path='.' HelloWorld

当然还有其他的方式可以指明路径请参考《在Linux平台下使用JNI》。

我们可以看到久违的“Hello world!”输出了。


分享文章:java代码编译so,Java代码编译过之后还可以重复编译吗
分享链接:http://ybzwz.com/article/hcodgh.html