美文网首页Android开发经验谈Android技术知识Android开发
“JNI” 在 Android 开发中的应用你了解多少?

“JNI” 在 Android 开发中的应用你了解多少?

作者: 程序老秃子 | 来源:发表于2022-05-31 15:51 被阅读0次

    JNI 简介

    JNI是Java Native Interface的缩写,通过使用 Java本地接口书写程序,可以确保代码在不同的平台上方便移植;从Java1.1开始,JNI标准成为java平台的一部分,它允许Java代码和其他语言写的代码进行交互

    本地代码与 Java 虚拟机之间是通过 JNI 函数实现相互操作的;JNI 函数通过接口指针来获得,本地方法将 JNI 接口指针当作参数来接受;虚拟机保证在从相同的 Java 线程中对本地方法进行多次调用时,传递给本地方法的接口指针是相同的,本地方法被不同的 Java 线程调用时,它接受不同的 JNI接口指针

    使用JNI和算法进行交互,主要是为了提高算法的性能,最大化的利用机器硬件资源

    Android 中的语言层

    可以将语言层分成Java层和Native层;为什么会有Native层呢?是因为在Java出现之前,很多的功能和系统都是由Native语言写的,所以Java出现之后就不必重复造轮子,直接调用这些方法就行了,而且Native层更接近汇编语言,所以性能更优

    所以代码中就出现了Java层调用Native层的方法,而这个跨语言的调用过程就是 JNI

    下图就是他们的关系:

    当Java语言无法处理一些任务的时候,就可以使用JNI来完成

    下面是几个 JNI 的应用场景:

    需要调用Java语言不支持的依赖于操作系统平台特性的一些功能

    ● 需要调用当前UNIX系统的某个功能,而Java不支持这个功能的时候,就要用到JNI

    ● 在程序对时间敏感或对性能要求特别高时,有必要用到更底层的语言来提高运行效率

    ● 音视频开发涉及到的音视频编解码需要更快的处理速度,这就需要用到JNI

    ● 为了整合一些以前的非Java语言开发的系统

    ● 需要用到早期实现的C/C++语言开发的一些功能或者系统,将这些功能整合到当前的系统或者新的版本中

    JNI是完善Java的一个重要功能,它让Java更加全面、封装了各个平台的差异性

    JNI在 Android 开发里的应用主要有:

    ● 音视频开发

    ● 热修复

    ● 插件化

    ● 逆向开发

    ● 等等…

    为了更好的使用JNI,Android提供了NDK这个工具,NDK基于JNI,所以理解了JNI,NDK也会很容易掌握

    JNI 中的引用类型

    Java中提供了四种引用类型,可以帮助垃圾回收。同样jni也提供了引用类型

    ● 本地引用(LocalReferences)

    ● 全局引用(Global References)

    ● 弱全局引用(Weak GlobalReferences)

    本地引用

    JNIEnv 提供的函数中定义的非全局的引用基本上都是本地引用,因此本地引用也是JNI中最常见的引用类型

    本地引用最大的特点当Native函数返回时,这个本地引用就会被自动释放;所以此引用是JVM负责的引用类型,受JVM管理

    我们也可以使用JNIEnv的DeleteLocalRef函数来手动删除本地引用

    全局引用

    在native函数返回时不会被自动释放,因此全局引用需要手动来进行释放,并且不会被GC回收

    JNIEnv的NewGlobalRef函数用来创建全局引用,调用JNIEnv的DeleteGlobalRef函数来释放全局引用

    全局引用不受到JVM管理

    弱全局引用

    是一种特殊的全局引用;它和全局引用的特点相似,不同的是弱全局是可以被GC回收的,弱全局引用被GC回收之后会指向NULL

    在运行过程中可能会被垃圾回收;所以使用它之前,需要调用 JNIEnv 的 isSameObject 判断它是否被回收

    JNI 的异常处理

    JNI 中也有异常,不过它和 C++、Java 的异常不太一样;如果调用 JNIEnv 的某些函数出错了,则会产生一个异常,但这个异常不会中断本地函数的执行,直到从 JNI 层返回到 Java 层后,虚拟机才会抛出这个异常

    虽然在 JNI 层中产生的异常不会中断本地函数的运行;但一旦产生异常后,就只能做一些资源清理工作了(例如释放全局引用,或者 ReleaseStringChars);如果这时调用除上面所说函数之外的其他 JNIEnv 函数,则会导致程序死掉

    JNI 层函数可以在代码中截获和修改这些异常,JNIEnv 提供了三个函数给予帮助:

    ● ExceptionOccured 函数,用来判断是否发生异常

    ● ExceptionClear 函数,用来清理当前 JNI 层中发生的异常

    ● ThrowNew 函数,用来向 Java 层抛出异常

    JNI 特点:

    二进制兼容

    ● 本地方法库与同一平台上所有Java 虚拟机之间实现二进制兼容,即对于给定平台开发人员只需要维护一种版本的本地方法库

    效率高

    为了实现实时系统,JNI 在效率与虚拟机无关性之间进行了优化,以保障高效运行

    功能强

    ● JNI 提供了大量的函数及接口让本地方法与Java 虚拟机内核相互操作,增强两者的功能

    本地代码与 Java 虚拟机之间是通过 JNI 函数实现相互操作的;JNI 函数通过接口指针来获得,本地方法将 JNI 接口指针当作参数来接受;虚拟机保证在从相同的 Java 线程中对本地方法进行多次调用时,传递给本地方法的接口指针是相同的,本地方法被不同的 Java 线程调用时,它接受不同的 JNI接口指针

    尾述

    点击 此处 即可 免费获取 更多学习笔记 面试视频

    技术是无止境的,你需要对自己提交的每一行代码、使用的每一个工具负责,不断挖掘其底层原理,才能使自己的技术升华到更高的层面

    Android 架构师之路还很漫长,与君共勉

    PS:有问题欢迎指正,可以在评论区留下你的建议和感受;
    欢迎大家点赞评论,觉得内容可以的话,可以转发分享一下

    相关文章

      网友评论

        本文标题:“JNI” 在 Android 开发中的应用你了解多少?

        本文链接:https://www.haomeiwen.com/subject/nwuzprtx.html