首页 > 编程语言 >Java中Native关键字的作用

Java中Native关键字的作用

时间:2022-12-16 11:02:46浏览次数:42  
标签:java 关键字 sayHello Java HelloNative Native 方法 native


初次遇见 native是在 java.lang.Object 源码中的一个hashCode方法:

​public native int hashCode();​

为什么有个native呢?这是我所要学习的地方。所以下面想要总结下native。

​​回到顶部​​

一、认识 native 即 JNI,Java Native Interface

凡是一种语言,都希望是纯。比如解决某一个方案都喜欢就单单这个语言来写即可。Java平台有个用户和本地C代码进行互操作的API,称为Java Native Interface (Java本地接口)。

 

 

​​回到顶部​​

二、用 Java 调用 C 的“Hello,JNI”

我们需要按照下班方便的步骤进行:

1、创建一个Java类,里面包含着一个 native 的方法和加载库的方法 loadLibrary。HelloNative.java 代码如下:

​public class HelloNative​

​{​

​static​

​{​

​System.loadLibrary("HelloNative");​

​}​

 

​public static native void sayHello();​

 

​@SuppressWarnings("static-access")​

​public static void main(String[] args)​

​{​

​new HelloNative().sayHello();​

​}​

​}​

首先让大家注意的是native方法,那个加载库的到后面也起作用。native 关键字告诉编译器(其实是JVM)调用的是该方法在外部定义,这里指的是C。如果大家直接运行这个代码,  JVM会告之:“A Java Exception has occurred.”控制台输出如下:

​Exception in thread "main" java.lang.UnsatisfiedLinkError: no HelloNative in java.library.path​

​at java.lang.ClassLoader.loadLibrary(Unknown Source)​

​at java.lang.Runtime.loadLibrary0(Unknown Source)​

​at java.lang.System.loadLibrary(Unknown Source)​

​at HelloNative.<​​​​clinit​​​​>(HelloNative.java:5)​

这是程序使用它的时候,虚拟机说不知道如何找到sayHello。下面既可以手动写,自然泥瓦匠是用

    2、运行javah,得到包含该方法的C声明头文件.h

将HelloNative.java ,简单地 javac javah,如图

 

就得到了下面的 HelloNative.h文件 

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

​#include <​​​​jni.h​​​​>​

​/* Header for class HelloNative */​

 

​#ifndef _Included_HelloNative​

​#define _Included_HelloNative​

​#ifdef __cplusplus​

​extern "C" {​

​#endif​

​/*​

​* Class:     HelloNative​

​* Method:    sayHello​

​* Signature: ()V​

​*/​

​JNIEXPORT void JNICALL Java_HelloNative_sayHello​

​(JNIEnv *, jclass);​

 

​#ifdef __cplusplus​

​}​

​#endif​

​#endif​

jni.h 这个文件,在/%JAVA_HOME%include

3、根据头文件,写C实现本地方法

这里我们简单地实现这个sayHello方法如下:

​#include "HelloNative.h"​

​#include <​​​​stdio.h​​​​>​

 

​JNIEXPORT void JNICALL Java_HelloNative_sayHello​

​{​

​printf("Hello,JNI");    ​

​}​

4、生成dll共享库,然后Java程序load库,调用即可。

在Windows上,MinGW GCC 运行如下

​gcc -m64  -Wl,--add-stdcall-alias -I"C:\Program Files\Java\jdk1.7.0_71\include" -I"C:\Program Files\Java\jdk1.7.0_71\include\include\win32" -shared -o HelloNative.dll HelloNative.c​

-m64表示生成dll库是64位的。然后运行 HelloNative:

​java HelloNative​

 

终于成功地可以看到控制台打印如下:

​Hello,JNI​

​​回到顶部​​

三、JNI 调用 C 流程图

Java中Native关键字的作用_JAVA

​​回到顶部​​

四、其他介绍

native是与C++联合开发的时候用的!java自己开发不用的!


使用native关键字说明这个方法是原生函数,也就是这个方法是用C/C++语言实现的,并且被编译成了DLL,由java去调用。
这些函数的实现体在DLL中,JDK的源代码中并不包含,你应该是看不到的。对于不同的平台它们也是不同的。这也是java的底层机制,实际上java就是在不同的平台上调用不同的native方法实现对操作系统的访问的。


1。native 是用做java 和其他语言(如c++)进行协作时用的
也就是native 后的函数的实现不是用java写的
2。既然都不是java,那就别管它的源代码了,呵呵


native的意思就是通知操作系统,
这个函数你必须给我实现,因为我要使用。
所以native关键字的函数都是操作系统实现的,
java只能调用。


java是跨平台的语言,既然是跨了平台,所付出的代价就是牺牲一些对底层的控制,而java要实现对底层的控制,就需要一些其他语言的帮助,这个就是native的作用了


Java不是完美的,Java的不足除了体现在运行速度上要比传统的C++慢许多之外,Java无法直接访问到操作系统底层(如系统硬件等),为此Java使用native方法来扩展Java程序的功能。
  可以将native方法比作Java程序同C程序的接口,其实现步骤:
  1、在Java中声明native()方法,然后编译;
  2、用javah产生一个.h文件;
  3、写一个.cpp文件实现native导出方法,其中需要包含第二步产生的.h文件(注意其中又包含了JDK带的jni.h文件);
  4、将第三步的.cpp文件编译成动态链接库文件;
  5、在Java中用System.loadLibrary()方法加载第四步产生的动态链接库文件,这个native()方法就可以在Java中被访问了。

JAVA本地方法适用的情况 
1.为了使用底层的主机平台的某个特性,而这个特性不能通过JAVA API访问

2.为了访问一个老的系统或者使用一个已有的库,而这个系统或这个库不是用JAVA编写的

3.为了加快程序的性能,而将一段时间敏感的代码作为本地方法实现。

标签:java,关键字,sayHello,Java,HelloNative,Native,方法,native
From: https://blog.51cto.com/lishuoboy/5946945

相关文章

  • JavaFX和swing、swt、awt 的区别?
    ......
  • Java并发多线程高频面试题
    并发知识不管在学习、面试还是工作过程中都非常非常重要,看完本文,相信绝对能助你一臂之力。1、线程和进程有什么区别?线程是进程的子集,一个进程可以有很多线程。每个进程都有......
  • 基于Java+Swing+mysql图书管理系统
    @目录一、系统介绍二、功能展示1.用户登陆2.系统主页3.图书查询4.图书添加5.图书修改6.图书删除7.办理借书8.办理还书9.历史查询10.用户查询、删除(管理员)三、数据库四、其......
  • 基于Java+Swing+mysql图书管理系统 (1)
    @目录一、系统介绍二、功能展示1.用户登陆2.图书管理3.图书添加4.图书类别管理5.图书类别添加三、数据库四、其它1.其他系统实现五、获取源码一、系统介绍程序中实现了登......
  • Java+Swing+mysql员工工资管理系统
    @目录一、系统介绍二、功能展示1.主页2.员工工资查询3.员工工资添加4.员工工资修改5.员工工资删除三、系统实现1.salary.java四、其它1.其他系统实现五、获取源码一、系统......
  • 【Java初阶】面向对象三大特性之继承
    一、继承理解继承Cat继承了Animal类,其中:Animal类称为父类/基类或超类,Cat可以称为Animal的子类/派生类,继承之后,子类可以复用父类中成员,子类在实现时只需关心自己新增加的成......
  • Flink 运行错误 java.lang.OutOfMemoryError: Direct buffer memory
    如遇到如下错误,表示需要调大配置项taskmanager.memory.framework.off-heap.size的值,taskmanager.memory.framework.off-heap.size的默认值为128MB,错误显示不够用需要调......
  • C# 与 Java 的区别
    C#与Java的区别C#最吸引人的地方是它与Java的区别而不是它们之间的相似性。下表是对C#和Java之间区别的简单介绍:序号JavaC#1Java是Oracle开发的......
  • Java8之list.stream的常见使用
    本文转自 https://blog.csdn.net/jhgnqq/article/details/123679622感谢楼主分享importorg.junit.Before;importorg.junit.Test;importjava.util.Arrays;import......
  • JAVA 百度坐标,火星坐标和WGS84之间互转
    百度坐标,但是在国内出于安全等相关因素考虑,在地图发布和出版的时,对WGS84坐标进行了一次非线性加偏,得到的坐标我们称之为GCJ02坐标系,俗称火星坐标,另外国内一些地图厂商出于......