JNI是Java Native Interface的缩写,中文为JAVA本地调用。使用JNI可以很方便的用我们的Java程序调用C/C++程序。很多时候,某些功能用Java无法实现,比如说涉及到底层驱动的一些功能,这时候我们就可以利用JNI来调用C或者C++程序来实现,这就是JNI的强大之处。但是JNI也有它的缺点,使用java与本地已编译的代码交互,通常会丧失平台可移植性。

  下面是一个JNI例子,调用C++输出"hello world":

第一步:创建Java类,在里面定义一个本地方法(用native关键字修饰的方法)

  public native void sayHello();

第二步:使用javah命令(javah  类的全路径)生成本地方法的C++头文件

  在DOS窗口中进入工程所在目录,然后执行javah com.test.TestNative命令,执行完之后就会在当前目录生成一个后缀名为.h的头文件,如com_test_TestNative.h,这个头文件是根据包名和类名来命名的。

 /* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class com_test_TestNative */ #ifndef _Included_com_test_TestNative
#define _Included_com_test_TestNative
#ifdef __cplusplus
extern "C" {
#endif
/*
* Class: com_test_TestNative
* Method: sayHello
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_com_test_TestNative_sayHello
(JNIEnv *, jobject); #ifdef __cplusplus
}
#endif
#endif

  15、16行是对TestNative类中的本地方法sayHello()的声明。这个h文件相当于我们在java里面的接口,这里声明了一个 Java_com_test_TestNative_sayHello (JNIEnv *, jobject);方法,然后在我们的本地方法里面实现这个方法,也就是说我们在编写C/C++程序的时候所使用的方法名必须和这里的一致。

第三步:编写C/C++本地代码,生成动态链接库文件

  首先在VC6.0(当然也可以用其他工具)中创建一个dll工程---Win32 Dynamic-Link Library工程。然后将上面生成的头文件com_test_TestNative.h添加到该工程中,然后创建一个源文件引用该头文件并且实现头文件中本地函数的功能:

     #include<iostream.h>
#include"com_test_TestNative.h" JNIEXPORT void JNICALL Java_com_test_TestNative_sayHello(JNIEnv *env, jobject obj)
{
cout<<"hello world!"<<endl;
}

  这里因为com_test_TestNative.h中引入了jni.h所以要将jni.h加入到VC6.0安装目录下的Include目录中。jni.h在JDK安装目录下的include中,同时得件include/win32中的两个头文件jawt_md.h、jni_md.h也导入到VC6.0中。

  将所依赖的头文件导入之后,我们就可以构建该工程了,按F7就行了,完了会在工程目录中的Degug目录下生成一个动态链接库文件,我这里生成的是NativeCode.dll。我们就可以将该dll文件拷贝到环境变量path所包含的目录下给咱们的Java程序调用了,为了方便,我们也可以将dll所在的工程目录加入到环境变量path中去,这样可以避免每次都要拷贝的麻烦。注意修改环境变量之后要重启myeclipse。

第四步:Java调用本地函数

 package com.test;

 public class TestNative {
public native void sayHello(); /**
* @param args
*/
public static void main(String[] args) {
System.loadLibrary("NativeCode");
TestNative tNative = new TestNative();
tNative.sayHello();
}
}

  第10行是加载动态链接库,JVM只需要加载一次就可以调用了,“NativeCode”是上面生成的动态链接库的名字,不含后缀名。

  运行该程序,成功打印输出了"hello world"。

Java通过JNI调用C++程序的更多相关文章

  1. JAVA使用JNI调用C++动态链接库

    JAVA使用JNI调用C++动态链接库 使用JNI连接DLL动态链接库,并调用其中的函数 首先 C++中写好相关函数,文件名为test.cpp,使用g++编译为DLL文件,指令如下: g++ -sha ...

  2. Java通过JNI调用dll详细过程(转)

    源:Java通过JNI调用dll详细过程 最近项目有这样一个需求,在已有的CS软件中添加一个链接,将当前登录用户的用户名加密后放在url地址中,在BS的login方法里通过解密判断,如果为合法用户则无 ...

  3. ubuntu下Java通过JNI调用C

    下面看一个实例,如下: public class TestJNI { static { System.loadLibrary("diaoyong"); // 程序在加载时,自动加载 ...

  4. Java通过jni调用动态链接库

    (1)JNI简介 JNI是Java Native Interface的缩写,它提供了若干的API实现了Java和其他语言的通信(主要是C&C++).从Java1.1开始,JNI标准成为java ...

  5. 第39篇-Java通过JNI调用C/C++函数

    在某些情况下,Java语言需要通过调用C/C++函数来实现某些功能,因为Java有时候对这些功能显的无能为力,如想使用X86_64 的 SIMD 指令提升一下业务方法中关键代码的性能,又或者想要获取某 ...

  6. Java通过JNI调用C

    Java调用C有多种方式,本文介绍笔者最近的学习过程,避免今后再犯类似的错误. 首先,Java肯定是调用C的动态链接库,即通过编译器编译后的dll/so文件. 下面介绍gcc编译dll的方法. 一般情 ...

  7. JAVA的JNI调用

    由于JNI调用C和调用C++差不多,而且C++中可以混合写C代码,所以这里主要是写关于JNI调用C++的部分. 一般步骤: 先是写普通的Java类,其中包括本地方法调用.  然后编译这个Java类,调 ...

  8. Cocos2d-x java 通过jni调用c++的方法

    前面博客说到,cocos2d-x c++界面层运行在一个GLThread线程里面,严格的说是运行在Cocos2dxGLSurfaceView(继承自GLSurfaceView) 里面.opengl的渲 ...

  9. 关于Java通过JNI调用C 动态链接库(DLL)

    JNI介绍 用JNI实现Java和C语言的数据传递 JNI原理分析和详细步骤截图说明 jni的JNIEnv指针和jobject指针 JNI实现回调| JNI调用JAVA函数|参数和返回值的格式 Jni ...

随机推荐

  1. python 全栈开发,Day21(抽象类,接口类,多态,鸭子类型)

    一.昨日复习 派生方法和派生属性 super 只有在子父类拥有同名方法的时候, 想使用子类的对象调用父类的方法时,才使用super super在类内 : super().方法名(arg1,..) 指名 ...

  2. 正确停止线程的方式三 使用Thread类中的内置的中断标记位-----------不熟悉

    package charpter10; public class Processor implements Runnable { @Override public void run() { for ( ...

  3. bootstrap之排版样式

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  4. php 发送超大数据处理

    set_time_limit(0);//设置永不超时 ignore_user_abort(); //设置客户端断开,继续处理 //总数 $allusercount= $this->gamedb_ ...

  5. hdu 1542

    链接:http://acm.hdu.edu.cn/showproblem.php?pid=1542 题意: 求所给矩形的覆盖面积 题解: 利用扫描线的思想,先将坐标离散化,之后以y轴分成多个矩形求解, ...

  6. c++ primer 笔记 (三)

    标准库类型string 和 vector ,分别定义了大小可变的字符串和集合.                 bitset,提供了一个抽象方法来操作位的集合.提供更方便的处理位的方式(相对于整型值上 ...

  7. Rookey.Frame v1.0快速开发平台-整体介绍

    Rookey.Frame v1.0是一套基于.NET MVC的极速开发框架,支持简单逻辑模块零代码编程.支持二次开发,具有高扩展性.高复用性.高伸缩性. 框架特点 (1)简单逻辑模块实现零代码编程,通 ...

  8. python日期与时间

    1.介绍 Python 提供了一个 time 和 calendar 模块可以用于格式化日期和时间. 时间间隔是以秒为单位的浮点小数. 每个时间戳都以自从1970年1月1日午夜(历元)经过了多长时间来表 ...

  9. @RequestParam注解使用:Name for argument type [java.lang.String] not available, and parameter name information not found in class file either.

    详细错误信息 Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Re ...

  10. 启动oracle command

    @echo off net start OracleXETNSListener >nul net start OracleServiceXE >nul