提交 7768fa46 编写于 作者: 沉默王二's avatar 沉默王二 💬

数据类型

上级 b7fc016e
......@@ -88,7 +88,7 @@
- [Java简介,什么是 Java?](docs/overview/what-is-java.md)
- [Java发展简史](docs/overview/java-history.md)
- [Java的特点,Java能做什么](docs/overview/java-can-do-what.md)
- [学Java还有前途吗?](docs/overview/java-can-do-what.md)
- [安装Java开发工具包JDK](docs/overview/jdk-install-config.md)
- [安装集成开发环境Intellij IDEA](docs/overview/IDEA-install-config.md)
- [编写第一个Java程序:Hello World](docs/overview/hello-world.md)
......@@ -97,7 +97,6 @@
## Java基础语法
- [Java中常用的48个关键字 & 2个保留字](docs/basic-extra-meal/48-keywords.md)
- [Java命名规范,告别编码 5 分钟,命名 2 小时](docs/basic-extra-meal/java-naming.md)
- [Java注释:单行、多行和文档注释](docs/basic-grammar/javadoc.md)
- [Java 中的数据类型(8 种基本数据类型和引用数据类型)](docs/basic-grammar/basic-data-type.md)
- [Java 数据类型转换(强制类型转换+自动类型转换)](docs/basic-grammar/type-cast.md)
......@@ -190,6 +189,7 @@
## Java重要知识点
- [Java命名规范](docs/basic-extra-meal/java-naming.md)
- [彻底弄懂Java中的Unicode和UTF-8编码](docs/basic-extra-meal/java-unicode.md)
- [Java中new Integer与Integer.valueOf的区别](docs/basic-extra-meal/int-cache.md)
- [深入剖析Java中的拆箱和装箱](docs/basic-extra-meal/box.md)
......
......@@ -107,7 +107,6 @@ export const sidebarConfig = sidebar({
collapsible: true,
children: [
"basic-extra-meal/48-keywords",
"basic-extra-meal/java-naming",
"basic-grammar/javadoc",
"basic-grammar/basic-data-type",
"basic-grammar/type-cast",
......@@ -229,6 +228,7 @@ export const sidebarConfig = sidebar({
prefix:"basic-extra-meal/",
collapsible: true,
children: [
"basic-extra-meal/java-naming",
"java-unicode",
"int-cache",
"box",
......
......@@ -12,7 +12,7 @@ head:
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java保留字,Java关键字,关键字,保留字
---
# 2.2.1 Java中常用的48个关键字和2个保留字
# 3.1 Java中常用的48个关键字和2个保留字
“二哥,就之前你给我展示的 Java 代码中,有 public、static、void、main 等等,它们应该都是关键字吧?”三妹的脸上泛着甜甜的笑容,我想她在学习 Java 方面已经变得越来越自信了。
......@@ -72,15 +72,15 @@ head:
26. **long:** 用于声明一个可以容纳 64 位整数的变量。
27. **native:** 用于指定一个方法是通过调用本机接口(非 Java)实现的
27. **native:** 用于指定一个[方法是通过调用本机接口(非 Java)实现的](https://tobebetterjavaer.com/oo/method.html)
28. **new:** 用于创建一个新的对象。
29. **null:** 如果一个变量是空的(什么引用也没有指向),就可以将它赋值为 null,和空指针异常息息相关。
30. **package:** 用于声明类所在的
30. **package:** 用于声明类所在的[](https://tobebetterjavaer.com/oo/package.html)
31. **private:** 一个访问权限修饰符,表示方法或变量只对当前类可见。
31. **private:** 一个[访问权限修饰符](https://tobebetterjavaer.com/oo/access-control.html),表示方法或变量只对当前类可见。
32. **protected:** 一个访问权限修饰符,表示方法或变量对同一包内的类和所有子类可见。
......@@ -90,34 +90,34 @@ head:
35. **short:** 用于声明一个可以容纳 16 位整数的变量。
36. **static:** 表示该变量或方法是静态变量或静态方法
36. **static:** 表示该变量或方法是[静态变量或静态方法](https://tobebetterjavaer.com/oo/static.html)
37. **strictfp:** 并不常见,通常用于修饰一个方法,确保方法体内的浮点数运算在每个平台上执行的结果相同。
38. **super:** 可用于调用父类的方法或者字段
38. **super:** 可用于[调用父类的方法或者字段](https://tobebetterjavaer.com/oo/this-super.html)
39. **switch:** 通常用于三个(以上)的条件判断。
40. **synchronized:** 用于指定多线程代码中的同步方法、变量或者代码块
40. **synchronized:** [用于指定多线程代码中的同步方法、变量或者代码块](https://tobebetterjavaer.com/thread/synchronized-1.html)
41. **this:** 可用于在方法或构造函数中引用当前对象
41. **this:** [可用于在方法或构造函数中引用当前对象](https://tobebetterjavaer.com/oo/this-super.html)
42. **throw:** 主动抛出异常
42. **throw:** 主动抛出[异常](https://tobebetterjavaer.com/exception/gailan.html)
43. **throws:** 用于声明异常。
44. **transient:** 修饰的字段不会被序列化
44. **transient:** [修饰的字段不会被序列化](https://tobebetterjavaer.com/io/transient.html)
45. **try:** 于包裹要捕获异常的代码块。
46. **void:** 用于指定方法没有返回值。
47. **volatile:** 保证不同线程对它修饰的变量进行操作时的可见性,即一个线程修改了某个变量的值,新值对其他线程来说是立即可见的。
47. **volatile:** 保证不同线程对它修饰的变量进行操作时的[可见性](https://tobebetterjavaer.com/thread/volatile.html),即一个线程修改了某个变量的值,新值对其他线程来说是立即可见的。
48. **while:** 如果循环次数不固定,建议使用 while 循环。
“好了,三妹,关于 Java 中的关键字就先说这 48 个吧,这只是一个大概的介绍,后面还会对一些特殊的关键字单独拎出来详细地讲,比如说重要的 static、final 等。”转动了一下僵硬的脖子后,我对三妹说。
“好了,三妹,关于 Java 中的关键字就先说这 48 个吧,这只是一个大概的介绍,后面还会对一些特殊的关键字单独拎出来详细地讲,比如说重要的 static、final 等。”转动了一下僵硬的脖子后,我对三妹说。
“除了这些关键字,Java 中还有两个非常特殊的保留字(goto 和 const),它们不能在程序中使用。”
......@@ -125,7 +125,7 @@ head:
“const 在 C语言中是声明常量的关键字,在 Java 中可以使用 public static final 三个关键字的组合来达到常量的效果。”
“好的二哥,我了解了,您辛苦了。”
“好的二哥,我了解了,你休息会,我再记一记。”
----
......
---
title: Java命名规范,告别编码 5 分钟,命名 2 小时
title: Java命名规范
shortTitle: Java命名规范
category:
- Java核心
......@@ -12,6 +12,8 @@ head:
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java命名规范,命名规范
---
## 3.2 Java命名规范
“二哥,Java 中的命名约定都有哪些呢?”三妹的脸上泛着甜甜的笑容,她开始对接下来要学习的内容充满期待了,这正是我感到欣慰的地方。
“对于我们中国人来说,名字也是有讲究的,比如说我叫沉默王二,你就叫沉默王三,哈哈。”我笑着对三妹说。
......@@ -24,6 +26,8 @@ head:
拿我这个笔名“沉默王二”来举例吧,读起来我就觉得朗朗上口,读者看到这个笔名就知道我是一个什么样的人——对不熟的人保持沉默,对熟的人妙语连珠,哈哈。
>当然了,如果你暂时记不住也没关系,后面再回头来记一下就好了。
### 01、包(package)
包的命名应该遵守以下规则:
......
---
title: Java 中的数据类型(8 种基本数据类型和引用数据类型)
shortTitle: Java 中的数据类型
title: Java中的数据类型(8种基本数据类型和引用数据类型)
shortTitle: Java中的数据类型
category:
- Java核心
tag:
......@@ -12,7 +12,7 @@ head:
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java 简介,Java数据类型,基本数据类型,引用数据类型,数据类型
---
## 数据类型的分类
# 2.3 Java中的数据类型(8种基本数据类型和引用数据类型)
“Java 是一种静态类型的编程语言,这意味着所有变量必须在使用之前声明好,也就是必须得先指定变量的类型和名称。”我吸了一口麦香可可奶茶后对三妹说。
......@@ -24,7 +24,7 @@ Java 中的数据类型可分为 2 种:
2)**引用数据类型**
除了基本数据类型以外的类型,都是所谓的引用类型。常见的有[数组](https://tobebetterjavaer.com/array/array.html)(对,没错,数组是引用类型)、class(也就是[](https://tobebetterjavaer.com/oo/object-class.html)),以及[接口](https://tobebetterjavaer.com/oo/interface.html)(指向的是实现接口的类的对象)。
除了基本数据类型以外的类型,都是所谓的引用类型。常见的有[数组](https://tobebetterjavaer.com/array/array.html)(对,没错,数组是引用类型,后面我们会讲)、class(也就是[](https://tobebetterjavaer.com/oo/object-class.html)),以及[接口](https://tobebetterjavaer.com/oo/interface.html)(指向的是实现接口的类的对象)。
来个思维导图,感受下。
......@@ -74,19 +74,19 @@ public class LocalVar {
| float | 0.0f | 4字节 |
| double | 0.0 | 8字节 |
## 比特和字节
### 比特和字节
那三妹可能要问,“比特和字节是什么鬼?”
比特币听说过吧?字节跳动听说过吧?这些名字当然不是乱起的,确实和比特、字节有关系。
比特币(Bitcoin)听说过吧?字节跳动(Byte Dance)听说过吧?这些名字当然不是乱起的,确实和比特、字节有关系。
### **1)bit(比特)**
#### **1)bit(比特)**
比特作为信息技术的最基本存储单位,非常小,但大名鼎鼎的比特币就是以此命名的,它的简写为小写字母“b”。
大家都知道,计算机是以二进制存储数据的,二进制的一位,就是 1 比特,也就是说,比特要么为 0 要么为 1。
### **2)Byte(字节)**
#### **2)Byte(字节)**
通常来说,一个英文字符是一个字节,一个中文字符是两个字节。字节与比特的换算关系是:1 字节 = 8 比特。
......@@ -96,11 +96,11 @@ public class LocalVar {
![](https://cdn.tobebetterjavaer.com/tobebetterjavaer/images/core-grammar/nine-03.png)
## 基本数据类型
### 基本数据类型
接下来,我们再来详细地了解一下 8 种基本数据类型。
### 01、布尔
#### 01、布尔
布尔(boolean)仅用于存储两个值:true 和 false,也就是真和假,通常用于条件的判断。代码示例:
......@@ -108,8 +108,7 @@ public class LocalVar {
boolean flag = true;
```
### 02、byte
#### 02、byte
byte 的取值范围在 -128 和 127 之间,包含 127。最小值为 -128,最大值为 127,默认值为 0。
......@@ -121,10 +120,7 @@ byte a = 10;
byte b = -10;
```
### 03、short
#### 03、short
short 的取值范围在 -32,768 和 32,767 之间,包含 32,767。最小值为 -32,768,最大值为 32,767,默认值为 0。代码示例:
......@@ -133,9 +129,7 @@ short s = 10000;
short r = -5000;
```
### 04、int
#### 04、int
int 的取值范围在 -2,147,483,648(-2 ^ 31)和 2,147,483,647(2 ^ 31 -1)(含)之间,默认值为 0。如果没有特殊需求,整型数据就用 int。代码示例:
......@@ -144,7 +138,7 @@ int a = 100000;
int b = -200000;
```
### 05、long
#### 05、long
long 的取值范围在 -9,223,372,036,854,775,808(-2^63) 和 9,223,372,036,854,775,807(2^63 -1)(含)之间,默认值为 0。如果 int 存储不下,就用 long,整型数据就用 int。代码示例:
......@@ -155,7 +149,7 @@ long b = -200000L;
为了和 int 作区分,long 型变量在声明的时候,末尾要带上大写的“L”。不用小写的“l”,是因为小写的“l”容易和数字“1”混淆。
### 06、float
#### 06、float
float 是单精度的浮点数,遵循 IEEE 754(二进制浮点数算术标准),取值范围是无限的,默认值为 0.0f。float 不适合用于精确的数值,比如说货币。代码示例:
......@@ -165,8 +159,7 @@ float f1 = 234.5f;
为了和 double 作区分,float 型变量在声明的时候,末尾要带上小写的“f”。不需要使用大写的“F”,是因为小写的“f”很容易辨别。
### 07、double
#### 07、double
double 是双精度的浮点数,遵循 IEEE 754(二进制浮点数算术标准),取值范围也是无限的,默认值为 0.0。double 同样不适合用于精确的数值,比如说货币。代码示例:
......@@ -188,7 +181,7 @@ Tips:单精度是这样的格式,1 位符号,8 位指数,23 位小数,
>一个数由若干位数字组成,其中影响测量精度的数字称作有效数字,也称有效数位。有效数字指科学计算中用以表示一个浮点数精度的那些数字。一般地,指一个用小数形式表示的浮点数中,从第一个非零的数字算起的所有数字。如 1.24 和 0.00124 的有效数字都有 3 位。
### 08、char
#### 08、char
char 可以表示一个 16 位的 Unicode 字符,其值范围在 '\u0000'(0)和 '\uffff'(65,535)(包含)之间。代码示例:
......@@ -203,7 +196,7 @@ char letterA = 'A'; // 用英文的单引号包裹住。
[关于字符编码](https://tobebetterjavaer.com/basic-extra-meal/java-unicode.html)
## 关于 int 和 char 类型互转
### 关于 int 和 char 类型互转
这里整理一波 int 和 char 类型的互转,它们之间比较特殊。也会在以后的学习当中经常遇到。
......@@ -260,8 +253,7 @@ int a = 'a';
因为发生了[自动类型转换](https://tobebetterjavaer.com/basic-grammar/type-cast.html)
## 引用数据类型
### 引用数据类型
基本数据类型在作为成员变量和静态变量的时候有默认值,引用数据类型也有的。
......@@ -290,7 +282,7 @@ null
null
```
null 在 Java 中是一个很神奇的存在,在你以后的程序生涯中,见它的次数不会少,尤其是伴随着令人烦恼的“[空指针异常](https://mp.weixin.qq.com/s/PBqR_uj6dd4xKEX8SUWIYQ)”,也就是所谓的 `NullPointerException`
null 在 Java 中是一个很神奇的存在,在你以后的程序生涯中,见它的次数不会少,尤其是伴随着令人烦恼的“[空指针异常](https://tobebetterjavaer.com/exception/npe.html)”,也就是所谓的 `NullPointerException`
也就是说,引用数据类型的默认值为 null,包括数组和接口。
......@@ -366,7 +358,6 @@ public class ArrayList<E> extends AbstractList<E>
![](https://cdn.tobebetterjavaer.com/tobebetterjavaer/images/core-grammar/nine-07.png)
只能 new 一个实现它的类的对象——那自然接口也是引用数据类型了。
来看一下基本数据类型和引用数据类型之间最大的差别。
......@@ -395,6 +386,39 @@ public class ArrayList<E> extends AbstractList<E>
这么说就理解了吧?
如果还不理解的话,可以看一下这个视频,讲的非常不错:[什么是堆?什么是栈?他们之间有什么区别和联系?](https://www.zhihu.com/question/19729973/answer/2238950166)
用图来表示一下,左侧是栈,右侧是堆。
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/basic-grammar/basic-data-type-dc26645a-3ed8-4ad4-815d-52528ad12d6b.png)
这里再补充一些额外的知识点,能看懂就继续吸收,看不懂可以先去学下一节,以后再来补,没关系的。学习就是这样,可以跳过,可以温故。
举个例子。
```java
String a = new String("沉默王二")
```
这段代码会先在堆里创建一个 沉默王二的字符串对象,然后再把对象的引用 a 放到栈里面。这里面还会涉及到[字符串常量池](https://tobebetterjavaer.com/string/constant-pool.html),后面会讲。
那么对于这样一段代码,有基本数据类型的变量,有引用类型的变量,堆和栈都是如何存储他们的呢?
```java
public void test()
{
int i = 4;
int y = 2;
Object o1 = new Object();
}
```
我来画个图表示下。
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/basic-grammar/basic-data-type-3d5b3e40-1abb-4624-8282-b83e58388825.png)
应该一目了然了吧?
“好了,三妹,关于 Java 中的数据类型就先说这么多吧,你是不是已经清楚了?”转动了一下僵硬的脖子后,我对三妹说。
---
......
......@@ -12,15 +12,14 @@ head:
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java 注释,javadoc,注释
---
# 2.2 Java注释:单行、多行和文档注释
“二哥,Java 中的注释好像真没什么可讲的,我已经提前预习了,不过是单行注释,多行注释,还有文档注释。”三妹的脸上泛着甜甜的笑容,她竟然提前预习了接下来要学习的知识,有一种“士别三日,当刮目相看”的感觉。
“注释的种类确实不多,但还是挺有意思的,且听哥来给你说道说道。”
![](https://cdn.tobebetterjavaer.com/tobebetterjavaer/images/overview/fourteen-01.png)
### 01、单行注释
单行注释通常用于解释方法内某单行代码的作用。
......
......@@ -97,7 +97,7 @@ head:
- [Java简介,什么是 Java?](overview/what-is-java.md)
- [Java发展简史](overview/java-history.md)
- [Java的特点,Java能做什么](overview/java-can-do-what.md)
- [学Java还有前途吗?](overview/java-can-do-what.md)
- [安装Java开发工具包JDK](overview/jdk-install-config.md)
- [安装集成开发环境Intellij IDEA](overview/IDEA-install-config.md)
- [编写第一个Java程序:Hello World](overview/hello-world.md)
......@@ -106,7 +106,6 @@ head:
### Java基础语法
- [Java中常用的48个关键字 & 2个保留字](basic-extra-meal/48-keywords.md)
- [Java命名规范,告别编码 5 分钟,命名 2 小时](basic-extra-meal/java-naming.md)
- [Java注释:单行、多行和文档注释](basic-grammar/javadoc.md)
- [Java 中的数据类型(8 种基本数据类型和引用数据类型)](basic-grammar/basic-data-type.md)
- [Java 数据类型转换(强制类型转换+自动类型转换)](basic-grammar/type-cast.md)
......@@ -199,6 +198,7 @@ head:
### Java重要知识点
- [Java命名规范](basic-extra-meal/java-naming.md)
- [彻底弄懂Java中的Unicode和UTF-8编码](basic-extra-meal/java-unicode.md)
- [Java中new Integer与Integer.valueOf的区别](basic-extra-meal/int-cache.md)
- [深入剖析Java中的拆箱和装箱](basic-extra-meal/box.md)
......
......@@ -12,8 +12,7 @@ head:
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,方法,实例方法,静态方法,抽象方法,java方法
---
“二哥,上一节学了Java 中的方法,这一节我们学什么呢?”三妹满是期待的问我。
“二哥,这一节我们学什么呢?”三妹满是期待的问我。
“这一节我们来了解一下 Java 中的方法——什么是方法?如何声明方法?方法有哪几种?什么是实例方法?什么是静态方法?什么是抽象方法?”我笑着对三妹说,“我开始了啊,你要注意力集中啊。”
......@@ -23,7 +22,6 @@ head:
只有方法被调用时,它才会执行。Java 中最有名的方法当属 `main()` 方法,这是程序的入口。
## 02、如何声明方法?
方法的声明反映了方法的一些信息,比如说可见性、返回类型、方法名和参数。如下图所示。
......@@ -39,7 +37,7 @@ head:
**返回类型**:方法返回的数据类型,可以是基本数据类型、对象和集合,如果不需要返回数据,则使用 void 关键字。
**方法名**:方法名最好反应出方法的功能,比如,我们要创建一个将两个数字相减的方法,那么方法名最好是 subtract。
**方法名**:方法名最好反应出方法的功能,比如,我们要创建一个将两个数字相减的方法,那么方法名最好是 subtract。
方法名最好是一个动词,并且以小写字母开头。如果方法名包含两个以上单词,那么第一个单词最好是动词,然后是形容词或者名词,并且要以驼峰式的命名方式命名。比如:
......@@ -54,7 +52,6 @@ head:
**方法体**:方法体放在一对花括号内,把一些代码放在一起,用来执行特定的任务。
## 03、方法有哪几种?
方法可以分为两种,一种叫预先定义方法,一种叫用户自定义方法。
......@@ -84,7 +81,6 @@ public class PredefinedMethodDemo {
预先定义方法让编程变得简单了起来,我们只需要在实现某些功能的时候直接调用这些方法即可,不需要重新编写。
### **2)用户自定义方法**
当预先定义方法无法满足我们的要求时,就需要自定义一些方法,比如说,我们来定义这样一个方法,用来检查数字是偶数还是奇数。
......@@ -217,14 +213,14 @@ public class StaticMethodExample {
StaticMethodExample 类中,mian 和 add 方法都是静态方法,不同的是,main 方法是程序的入口。当我们调用静态方法的时候,就不需要 new 出来类的对象,就可以直接调用静态方法了,一些工具类的方法都是静态方法,比如说 hutool 工具类库,里面有大量的静态方法可以直接调用。
>Hutool的目标是使用一个工具方法代替一段复杂代码,从而最大限度的避免“复制粘贴”代码的问题,彻底改变我们写代码的方式。
> Hutool 的目标是使用一个工具方法代替一段复杂代码,从而最大限度的避免“复制粘贴”代码的问题,彻底改变我们写代码的方式。
以计算MD5为例:
以计算 MD5 为例:
- 👴【以前】打开搜索引擎 -> 搜“Java MD5加密” -> 打开某篇博客-> 复制粘贴 -> 改改好用
- 👦【现在】引入Hutool -> SecureUtil.md5()
- 👴【以前】打开搜索引擎 -> 搜“Java MD5 加密” -> 打开某篇博客-> 复制粘贴 -> 改改好用
- 👦【现在】引入 Hutool -> SecureUtil.md5()
Hutool的存在就是为了减少代码搜索成本,避免网络上参差不齐的代码出现导致的bug。
Hutool 的存在就是为了减少代码搜索成本,避免网络上参差不齐的代码出现导致的 bug。
## 06、什么是抽象方法?
......@@ -264,11 +260,175 @@ public class MyAbstractDemo extends AbstractDemo {
重写了抽象方法
```
----
## 07、什么是本地 native 方法?
类似 Thread 类中的 `private native start0()` 方法;
又或者 Object.class 类中的 getClass() 方法、hashCode()方法、clone() 方法,其中方法签名如下:
```java
public final native Class<?> getClass();
public native int hashCode();
protected native Object clone() throws CloneNotSupportedException;
```
也就是用【native】关键词修饰的方法,多数情况下不需要用 Java 语言实现。
“二哥,为什么要用 native 来修饰方法呢,这样做有什么用?”三妹很乖,但这个问题也问的很掷地有声。
“好的,三妹,我们一步步来扒拉”。
### **1、JNI:Java Native Interface**
在介绍 native 之前,我们先了解什么是 JNI。
一般情况下,我们完全可以使用 Java 语言编写程序,但某些情况下,Java 可能满足不了需求,或者不能更好的满足需求,比如:
- ①、标准的 Java 类库不支持。
- ②、我们已经用另一种语言,比如说 C/C++ 编写了一个类库,如何用 Java 代码调用呢?
- ③、某些运行次数特别多的方法,为了加快性能,需要用更接近硬件的语言(比如汇编)编写。
上面这三种需求,说到底就是如何用 Java 代码调用不同语言编写的代码。那么 JNI 应运而生了。
从 Java 1.1 开始,Java Native Interface (JNI)标准就成为 Java 平台的一部分,它允许 Java 代码和其他语言编写的代码进行交互。
JNI 一开始是为了本地已编译语言,尤其是 C 和 C++而设计的,但是它并不妨碍你使用其他语言,只要调用约定受支持就可以了。使用 Java 与本地已编译的代码交互,通常会丧失平台可移植性,但是,有些情况下这样做是可以接受的,甚至是必须的,比如,使用一些旧的库,与硬件、操作系统进行交互,或者为了提高程序的性能。JNI 标准至少保证本地代码能工作能在任何 Java 虚拟机实现下。
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-67e26e52-bf45-4126-a516-1e768632aaa8.jpg)
通过 JNI,我们就可以通过 Java 程序(代码)调用到操作系统相关的技术实现的库函数,从而与其他技术和系统交互;同时其他技术和系统也可以通过 JNI 提供的相应原生接口调用 Java 应用系统内部实现的功能。
在 Windows 上,一般可执行的应用程序都是基于 native 的 PE 结构,Windows 上的 JVM 也是基于 native 结构实现的。Java 应用体系都是构建于 JVM 之上。
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-61f0597a-b164-4128-a55d-1ee65189eae1.jpg)
“二哥,等一下,Java 不是跨平台的吗?如果用 JNI,那么程序不就失去了跨平台的优点?”不得不说,三妹这个问题起到好处。
“确实是这样的。”我掐灭了中指和无名指之间的烟头,继续娓娓道来。
JNI 的缺点:
- ①、程序不再跨平台。要想跨平台,必须在不同的系统环境下重新编译本地语言部分。
- ②、程序不再是绝对安全的,本地代码的不当使用可能导致整个程序崩溃。一个通用规则是,你应该让本地方法集中在少数几个类当中。这样就降低了 Java 和 C/C++ 之间的耦合性。
目前来讲使用 JNI 的缺点相对于优点还是可以接受的,可能后面随着 Java 的技术发展,我们不在需要 JNI,但是目前 JDK 还是一直提供了对 JNI 标准的支持。
### **3、用 C 语言编写程序本地方法**
“上面讲解了什么是 JNI,接下来我们来写个例子:如何用 Java 代码调用本地的 C 程序。”我扭头对三妹说,“你注意📢看。”
>官方文档如下:[https://docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/jniTOC.html](https://link.zhihu.com/?target=https%3A//docs.oracle.com/javase/8/docs/technotes/guides/jni/spec/jniTOC.html)
步骤如下:   
①、编写带有 native 方法的 Java 类,生成.java 文件;
②、使用 javac 命令编译所编写的 Java 类,生成.class 文件;
③、使用 javah -jni java 类名 生成扩展名为 h 的头文件,也即生成 .h 文件;
④、使用 C/C++(或者其他编程想语言)实现本地方法,创建 .h 文件的实现,也就是创建 .cpp 文件实现.h 文件中的方法;
⑤、将 C/C++ 编写的文件生成动态连接库,生成 dll 文件;
下面我们通过一个 HelloWorld 程序的调用来完成这几个步骤。
>注意:下面所有操作都是在所有操作都是在目录:D:\\JNI 下进行的。
#### 一、编写带有 native 声明的方法的 java 类
```text
public class HelloJNI {
//native 关键字告诉 JVM 调用的是该方法在外部定义
private native void helloJNI();
static{
System.loadLibrary("helloJNI");//载入本地库
}
public static void main(String[] args) {
HelloJNI jni = new HelloJNI();
jni.helloJNI();
}
}
```
用 native 声明的方法告知 JVM 调用该方法在外部定义,也就是我们会用 C 语言去实现。
`System.loadLibrary("helloJNI");`加载动态库,参数 helloJNI 是动态库的名字。我们可以这样理解:程序中的方法 helloJNI() 在程序中没有实现,但是我们下面要调用这个方法,怎么办呢?我们就需要对这个方法进行初始化,所以用了 [static 代码块进行初始化](https://tobebetterjavaer.com/oo/static.html)
这时候如果我们直接运行该程序,会报“A Java Exception has occurred”错误:
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-b5a7e2d8-5bae-45ae-8225-6c21090b506a.jpg)
#### 二、使用 javac 命令编译 java 类,生成.class 文件
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-1131ccf8-e4d0-4e4c-b7f6-659f0906c5d4.jpg)
执行上述命令后,生成 HelloJNI.class 文件:
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-b015e4ae-d636-42ef-93e7-381e33587ea9.jpg)
#### 三、使用 javah -jni java 类名 生成扩展名为 h 的头文件
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-0f2755b6-45ad-44d6-88ff-2eb3fa5cba3b.jpg)
执行上述命令后,在 D:/JNI 目录下会多出一个 HelloJNI.h 文件:
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-7798a73c-1fdf-4f08-9d29-9ee5dfaa8a1b.jpg)
#### 四、使用 C 语言实现本地方法   如果不想安装 Visual Studio,需要在 Windows 平台安装 gcc。
安装教程如下:[http://blog.csdn.net/altland/article/details/63252757](https://blog.csdn.net/altland/article/details/63252757)
注意安装版本的选择,根据系统是 32 位还是 64 位来选择。
安装完成之后注意配置环境变量,在 cmd 中输入 `g++ -v`,如果出现如下信息,则安装配置完成:
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-43b26326-e461-4b55-b029-d8b8e745ecbe.jpg)
接着输入如下命令:
```
gcc -m64 -Wl,--add-stdcall-alias -I"C:\Program Files\Java\jdk1.8.0_152\include" -I"C:\Program Files\Java\jdk1.8.0_152\include\include\win32" -shared -o helloJNI.dll helloJNI.c
```
\-m64 表示生成 dll 库是 64 位的。后面的路径表示本机安装的 JDK 路径。生成之后多了一个 helloJNI.dll 文件
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-07eabf6b-166a-4537-9521-8781887e4ad7.jpg)
最后运行 HelloJNI:输出 Hello JNI! 大功告成。
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-541e9154-1643-42f7-9baf-357405466711.jpg)
### **4、JNI 调用 C 的流程图**
![](http://cdn.tobebetterjavaer.com/tobebetterjavaer/images/oo/method-a2103240-def4-460f-a12c-8f74e08e2b1b.jpg)
### **5、native 关键字**
“三妹,现在应该知道什么是 native 了吧?”我问三妹。
“嗯嗯,我来简述一下,二哥你看看我说的是否正确。”
native 用来修饰方法,用 native 声明的方法表示该方法的实现在外部定义,可以用任何语言去实现它,比如说 C/C++。 简单地讲,一个 native Method 就是一个 Java 调用非 Java 代码的接口。
native 语法:
- ①、修饰方法的位置必须在返回类型之前,和其余的方法控制符前后关系不受限制。
- ②、不能用 abstract 修饰,也没有方法体,也没有左右大括号。
- ③、返回值可以是任意类型
“三妹,你学的不错嘛。”我对三妹的学习能力感到非常的欣慰,“**我们在日常编程中看到 native 修饰的方法,只需要知道这个方法的作用是什么,至于别的就不用管了,操作系统会给我们实现**。”
>参考链接:[https://www.zhihu.com/question/28001771/answer/2049534464](https://www.zhihu.com/question/28001771/answer/2049534464)
---
最近整理了一份牛逼的学习资料,包括但不限于Java基础部分(JVM、Java集合框架、多线程),还囊括了 **数据库、计算机网络、算法与数据结构、设计模式、框架类Spring、Netty、微服务(Dubbo,消息队列) 网关** 等等等等……详情戳:[可以说是2022年全网最全的学习和找工作的PDF资源了](https://tobebetterjavaer.com/pdf/programmer-111.html)
最近整理了一份牛逼的学习资料,包括但不限于 Java 基础部分(JVM、Java 集合框架、多线程),还囊括了 **数据库、计算机网络、算法与数据结构、设计模式、框架类 Spring、Netty、微服务(Dubbo,消息队列) 网关** 等等等等……详情戳:[可以说是 2022 年全网最全的学习和找工作的 PDF 资源了](https://tobebetterjavaer.com/pdf/programmer-111.html)
微信搜 **沉默王二** 或扫描下方二维码关注二哥的原创公众号沉默王二,回复 **111** 即可免费领取。
![](https://cdn.tobebetterjavaer.com/tobebetterjavaer/images/gongzhonghao.png)
\ No newline at end of file
![](https://cdn.tobebetterjavaer.com/tobebetterjavaer/images/gongzhonghao.png)
---
title: Java的特点,Java能做什么
shortTitle: Java的特点
title: 学 Java 还有前途吗?
shortTitle: 学Java还有前途吗?
category:
- Java核心
tag:
- Java概述
description: Java程序员进阶之路,小白的零基础Java教程,Java的优势,Java的特点,Java能做什么
description: Java程序员进阶之路,小白的零基础Java教程,Java的优势,Java的特点,Java能做什么,学 Java 有前途吗?
head:
- - meta
- name: keywords
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java 优势,特点
content: Java,Java SE,Java基础,Java教程,Java程序员进阶之路,Java入门,教程,Java 优势,特点,java前途
---
# 2.3 Java的特性和应用领域
# 2.3 学 Java 还有前途吗?
尽管 Java 已经 25 岁了,但仍然“宝刀未老”。在 Stack Overflow 2019 年流行编程语言调查报告中,Java 位居第 5 位,有 41% 的受调开发者认为 Java 仍然是一门受欢迎的编程语言。
......
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册