Java的JNI快速入门教程(推荐)

1. JNI简介

JNI是Java Native Interface的英文缩写,意为Java本地接口。

问题来源:由于Java编写底层的应用较难实现,在一些实时性要求非常高的部分Java较难胜任(实时性要求高的地方目前还未涉及,实时性这类话题有待考究)。

解决办法:Java使用JNI可以调用现有的本地库(C/C++开发任何和系统相关的程序和类库),极大地灵活Java的开发。

2. JNI快速学习教程

2.1 问题:

使用JNI写一段代码,实现string_Java_Test_helloworld(JNIEnv *env, jclass cls , jstring j_str)函数,实现在字符串j_str("world")前面加上hello,并返回。

2.2 解决问题过程:

I. 编写Test.java类:

public class Test{
  // native interface
  public native String helloworld(String text);

  public static void main(String[] args){
    // Load dynamic library
    System.loadLibrary("Test2");
    Test ts = new Test();
    String text = ts.helloworld("world");
    System.out.println(text);
  }
}

备注:

1、加载动态类库:System.loadLibrary("Test2");【Windows下加载的就是Test2.dll,Linux下加载的是Test2.so】

II. 编译Test.java文件

进入cmd输入命令 > javac Test.java

III. 生成Test.h文件

进入cmd输入命令 > javah Test

Test.h文件内容如下:

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class Test */

#ifndef _Included_Test
#define _Included_Test
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:   Test
 * Method:  helloworld
 * Signature: (Ljava/lang/String;)Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_Test_helloworld
 (JNIEnv *, jobject, jstring);

#ifdef __cplusplus
}
#endif
#endif

备注:

1、函数声明,固定格式:JNIEXPORT;返回类型:jstring;JNI调用:JNICALL;Java_完整类名_方法名:Java_Test_helloworld;

2、函数参数:调用jni.h封装好的函数指针:JNIEnv;Java类本身:jobject,Java文件传入参数:jstring。

IV. 编写C语言文件Test2.c实现Test类调用动态链接库的功能:

#include "Test.h"
#include <string.h>

JNIEXPORT jstring JNICALL Java_Test_helloworld
 (JNIEnv *env, jobject obj, jstring string){
  const char* str = (*env)->GetStringUTFChars(env,string,0);
  char cap[128];
  cap[0] = 'h';
  cap[1] = 'e';
  cap[2] = 'l';
  cap[3] = 'l';
  cap[4] = 'o';

  strcat(cap,str);

  (*env)->ReleaseStringUTFChars(env,string,0);
  return (*env)->NewStringUTF(env,cap);
 }

备注:

1、由于Java本身使用了双字节字符,C语言本身都是单字节字符,所以需要使用(*env)->GetStringUTFChars()转换Java和C之间的字符串;

2、GetStringUTFChars()和NewStringUTF(),第一个是从UTF8转换为C的编码格式,第二个是根据C的字符串返回一个UTF8字符串;

3、ReleaseStringUTFChars()是用来释放对象的,在Java中有虚拟机进行垃圾回收,但是在C语言中这些对象必须手动回收,否则可能造成内存泄漏。

V. 编译和运行

编译:

进入cmd输入命令 > gcc -I "D:\Program Files\Java\jdk1.8.0_45\include" -I "D:\Program Files\Java\jdk1.8.0_45\include\win32" --share Test2.c -o Test2.dll

运行:

进入cmd输入命令 > java Test

运行结果如下:

helloworld

3. 总结:

第一步:编写带有native方法的Java类(Test.java),使用javac工具编译Java类(生成Test.class);

第二步:使用javah生成与native方法对应的头文件(Test.h);

第三步:使用C/C++实现相应的头文件(Test2.c),并编译为动态链接库(Test2.so)。

本文运行环境:Windows 64位操作系统,JDK 1.8版本,mingw64(GCC)。

以上这篇Java的JNI快速入门教程(推荐)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们。

(0)

相关推荐

  • 较详细的JNI简介

    在Java中,有时候我们不得不要去使用其他语言的代码,比如说: 1.你的应用需要访问系统的各个特性和设备,这些特性和设备通过java平台是无法访问的. 2.你已经有了大量的测试过和调试过的用另一种语言编写的代码,并且知道如何将其导出到所有的目标平台上. 3.通过基础测试,你已经发现所编写的Java代码比用其他语言编写的等价代码要慢得多. Java平台有一个用于和本地C代码进行互操作的API,称为Java本地接口(JNI).现在就开始学习JNI,先从这篇的一个最简单的例子,了解如何使用JNI调用本

  • Ubuntu 使用Jni开发实例详解

    1. 编写Java文件,在其中声明native方法, 并通过static 语句块加载动态链接库,示例Prompt.java代码如下: class Prompt { private native String getLine(String prompt); public static void main(String args[]) { Prompt p = new Prompt(); String input = p.getLine("Type a line: "); System.o

  • 从源码编译Android系统的Java类库和JNI动态库的方法

    利用源码编译Android系统Java类库 1.编写Java项目和Android.mk文件 ├── Android.mk └── src └── com └── lhw └── framework └── led └── Led.java Led.java文件 package com.lhw.framework.led; /** * LED操作库 * @author Micky Liu */ public class Led { public boolean turnOn() { return

  • 启动 Eclipse 弹出 Failed to load the JNI shared library jvm.dll 错误的解决方法

    错误如下图所示: 有时候,新电脑上回碰到打开Eclipse时,弹出提示"Failed to load the JNI shared library jvm.dll"错误,这里给大家分享解决方案. 通常情况下,如果你是64位的系统,却安装了32位的JDK,就会导致上面的情况. 解决办法 1.卸载掉原来安装的32位的JDK,然后安装64位的JDK到电脑中. 2.重新修改path 和 classpath 两个环境变量.因为在64系统当中,32位软件回安装到program files (*86

  • Android通过JNI实现守护进程

    开发一个需要常住后台的App其实是一件非常头疼的事情,不仅要应对国内各大厂商的ROM,还需要应对各类的安全管家...虽然不断的研究各式各样的方法,但是效果并不好,比如任务管理器把App干掉,服务就起不来了... 网上搜寻一番后,主要的方法有以下几种方法,但都是治标不治本: 1.提高Service的优先级:这个,也只能说在系统内存不足需要回收资源的时候,优先级较高,不容易被回收,然并卵... 2.提高Service所在进程的优先级:效果不是很明显 3.在onDestroy方法里重启service:

  • Java的JNI快速入门教程(推荐)

    1. JNI简介 JNI是Java Native Interface的英文缩写,意为Java本地接口. 问题来源:由于Java编写底层的应用较难实现,在一些实时性要求非常高的部分Java较难胜任(实时性要求高的地方目前还未涉及,实时性这类话题有待考究). 解决办法:Java使用JNI可以调用现有的本地库(C/C++开发任何和系统相关的程序和类库),极大地灵活Java的开发. 2. JNI快速学习教程 2.1 问题: 使用JNI写一段代码,实现string_Java_Test_helloworld

  • Jupyter notebook快速入门教程(推荐)

    本文主要介绍了Jupyter notebook快速入门教程,分享给大家,具体如下: 本篇将给大家介绍一款超级好用的工具:Jupyter notebook. 为什么要介绍这款工具呢? 如果你想使用Python学习数据分析或数据挖掘,那么它应该是你第一个应该知道并会使用的工具,它很容易上手,用起来非常方便,是个对新手非常友好的工具.而事实也证明它的确很好用,在数据挖掘平台 Kaggle 上,使用 Python 的数据爱好者绝大多数使用 jupyter notebook 来实现分析和建模的过程,因此,

  • ReactJs快速入门教程(精华版)

    现在最热门的前端框架有AngularJS.React.Bootstrap等.自从接触了ReactJS,ReactJs的虚拟DOM(Virtual DOM)和组件化的开发深深的吸引了我,下面来跟我一起领略ReactJs的风采吧~~ 文章有点长,耐心读完,你会有很大收获哦~   一.ReactJS简介 React 起源于 Facebook 的内部项目,因为该公司对市场上所有 JavaScript MVC 框架,都不满意,就决定自己写一套,用来架设 Instagram 的网站.做出来以后,发现这套东西

  • 基于Bootstrap框架菜鸟入门教程(推荐)

    Bootstrap菜鸟入门教程 Bootstrap简介 Bootstrap,来自 Twitter,是目前最受欢迎的前端框架.Bootstrap 是基于 HTML.CSS.JAVASCRIPT 的,它简洁灵活,使得 Web 开发更加快捷. 一.栅格系统 栅格系统的工作原理: "行(row)"必须包含在 .container (固定宽度)或 .container-fluid (100% 宽度)中,以便为其赋予合适的排列(aligment)和内补(padding). 通过"行(ro

  • Vue.js快速入门教程

    像AngularJS这种前端框架可以让我们非常方便地开发出强大的单页应用,然而有时候Angular这种大型框架对于我们的项目来说过于庞大,很多功能不一定会用到.这时候我们就需要评估一下使用它的必要性了.如果我们仅仅需要在一个简单的网页里添加屈指可数的几个功能,那么用Angular就太麻烦了,必要的安装.配置.编写路由和设计控制器等等工作显得过于繁琐. 这时候我们需要一个更加轻量级的解决方案.Vue.js就是一个不错的选择.Vue.js是一个专注于视图模型(ViewModal)的框架.视图模型是U

  • Java中Jackson快速入门

    Java生态圈中有很多处理JSON和XML格式化的类库,Jackson是其中比较著名的一个.虽然JDK自带了XML处理类库,但是相对来说比较低级,使用本文介绍的Jackson等高级类库处理起来会方便很多. 引入类库 由于Jackson相关类库按照功能分为几个相对独立的,所以需要同时引入多个类库,为了方便我将版本号单独提取出来设置,相关Gradle配置如下. ext { jacksonVersion = '2.9.5' } dependencies { compile group: 'com.fa

  • Springboot快速入门教程

    入门Springboot 项目创建在IDEA中创建即可. 注意点: 1.所有文件都需要放在 : Application文件的同级或下级目录中 2.application.properties 为 spring-boot 项目主核心配置文件,且只能有一个核心配置文件. 3.多环境下的核心配置文件的使用, 文件名必须以 application- 开头!   application-xxx.properties (1)开发环境 # 开发环境配置文件 server.port=9000 server.se

  • Unity3D快速入门教程

    Unity3D游戏引擎介绍 Unity3D是由Unity Technologies开发的一个让玩家轻松创建诸如三维视频游戏.建筑可视化.实时三维动画等类型互动内容的多平台的综合型游戏开发工具,是一个全面整合的专业游戏引擎.使用Unity3D,开发者可以快速的开发出游戏.Unity3D引擎占据了游戏引擎市场45%的份额,居全球首位.因此,学习游戏开发,Unity3D的人才需求量最为庞大. Unity3D学习历程 俗话说,万事开头难.Unity3D的学习历程也是一样.学习Unity3D,大致分为以下

  • MyBatis-Plus简介和快速入门教程

    目录 一.MyBatis-Plus简介(来自官网) 二.快速开始 三.通用CRUD 3.1 insert(插入操作) 3.2 updateById(更新操作) 3.3 查询操作--各种select 3.4 删除操作--各种delete 附加1:如果表名或者表中属性的名称与我们实体类的名称不同解决方法 一.MyBatis-Plus简介(来自官网) MyBatis-Plus,简称MP,是一个MyBatis的增强工具,在MyBatis的基础上只做增强不做修改,为简化开发.提高效率而生. 特性: 无侵入

  • SparkSQL快速入门教程

    目录 (一)概述 (二)SparkSQL实战 (三)非JSON格式的Dataset创建 (四)通过JDBC创建DataFrame (五)总结 (一)概述 SparkSQL可以理解为在原生的RDD上做的一层封装,通过SparkSQL可以在scala和java中写SQL语句,并将结果作为Dataset/DataFrame返回.简单来讲,SparkSQL可以让我们像写SQL一样去处理内存中的数据. Dataset是一个数据的分布式集合,是Spark1.6之后新增的接口,它提供了RDD的优点和Spark

随机推荐