Chap11:JNI编程系列之基础篇

32 篇文章 0 订阅

JNI编程系列之基础篇

 

最近干一个活需要从Java调用C++编译的动态链接库,研究了一下JNI,现在将网上搜罗的文档和自己的体会贡献出来。

 

JNI的做法是:通过在方法前加上关键字native来识别本地方法,然后用本地语言(CC++)来实现该方法,并编译成动态链接库,在Java的类中调用该动态链接库,然后就可以像使用Java自己的方法一样使用native方法了。这样做的好处是既具有了Java语言的便利性,又具有了C语言的效率;另一个好处是可以利用已有的C代码,避免重复开发。

下面从最简单的JNI程序入手,介绍如何进行JNI编程。

 

 

下面是一个简单的Java程序HelloWorld.java

 

class HelloWorld {

private native void print();

public static void main(String[] args) {

new HelloWorld().print();

}

static {

System.loadLibrary("HelloWorld");

}

}

 

在这个例子中,注意到两个关键的地方。

首先是第二行

private native void print();

如果没有native关键字,这一行代码就是普通Java方法的声明。关键字native表明这是一个用本地语言实现的方法。

第二个地方是

System.loadLibrary("HelloWorld");

这行代码的作用是调用名为HelloWorld的动态链接库,在Windows下,是HelloWorld.dll,在Linux下是HelloWorld.so

 

显然现在这个Java程序是不能运行的。要运行它先要做下面的工作。执行

> javac HelloWorld.java

> javah -jni HelloWorld

 

执行完这两条语句之后,会生成一个名为HelloWorld.h的文件,它的内容应该是这样的,

 

 

/* DO NOT EDIT THIS FILE - it is machinegenerated */

#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 JNICALLJava_HelloWorld_print (JNIEnv *, jobject);

#ifdef __cplusplus

}

#endif

#endif

 

 

 

注意到在这个程序的开头有这样一行代码,

#include <jni.h>

这里的jni.h,只要你安装了JDK就能在安装目录下找到它。

不要修改这个文件的内容,现在要做的是写一个名为HelloWorld.cpp程序,实现上面这个.h文件里的函数,

 

//------------

#include "HelloWorld.h"

#include <iostream>

JNIEXPORT void JNICALLJava_HelloWorld_print (JNIEnv *, jobject) {

std::cout << "Hello World!"<< std::endl;

}

//--------------

 

这是一个最简单的C++程序。将它编译为动态链接库,我们得到HelloWorld.dll,将这个.dll文件拷到HelloWorld.java文件所在的目录下。执行

> java HelloWorld

你会看到屏幕上输出

> Hello World!

 

 

现在来总结一下,要实现JNI编程,需要以下几个步骤:

1. 写一个Java程序,将你希望用C语言实现的方法用native关键字标识出来,同时加上调用动态链接库的语句。

   System.loadLibrary("HelloWorld");

2. 执行下面两条语句,生成.h文件

  

  

   > javac HelloWorld.java

  

classbin目录下(其下或其子目录下有 javac命令生成的*.class文件)执行

   > javah -jni HelloWorld

3. 根据.h文件,写一个.cpp程序,编译成动态链接库,并将其复制到.java文件所在的路径下。

4. 执行java HelloWorld

这样,就学会了最简单的JNI编程,网上能google到的大部分文章也就到此为止了。但是你一定还有很多疑问,就像我刚开始一样,最容易想到的就是,如果本地方法要传递参数或者返回值怎么办?本地方法的定义在.java文件中,参数或者返回值的类型都是Java的类型。而它的实现是通过C程序完成的,参数和返回值的类型只能是C的类型。诸如此类的问题,上面这个简单的例子是回答不了的。在下一篇,我将解释这些问题。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值