文档章节

关于 JDK 9 中的 JShell,你应该了解的 10 件事

红薯
 红薯
发布于 04/06 08:30
字数 1461
阅读 3110
收藏 42

JShell 是在 JDK 9 中首次引入的,以 Kulla 实现的 Java Enhancement Proposal (JEP) 222 规范的一部分。很多编程语言如 JavaScript、Python、Ruby 等,提供了非常易用的命令行执行工具,但 Java 一直缺失此功能。因此 JDK 9 引入了 Java shell 工具 —— JShell。

在之前的 文章 中我们曾经讨论了 JShell 的一些基础知识,这篇文字中我们主要聊一些高级的概念。

1. 变量重新定义

在 Java 中,我们是没法对一个变量进行重新声明的。但是有了 JShell,我们可以随时在需要的时候对一个变量重新进行定义,包括原生类型以及引用类型变量。

示例:

jshell> String str="Hello"
str ==> "JShell"
jshell> Integer str=10
str ==> 10

2. 临时变量 (Scratch Variables)

在 JShell 命令行中可以将任意表达式计算的结果赋值给变量,尽管你并没有显式的赋值。这样的变量称为临时变量。例如:

jshell> "Hello"+"JShell"
$1 ==> "HelloJShell"

请注意为了让 JShell 知道变量类型以及表达式计算的详细信息,我们可以设置 feeback 为详细模式:

/set feedback verbose
jshell> 60+10
$2 ==> 70
|  created scratch variable $21 : int

要退出详细模式,只需转回正常模式即可:

/set feedback normal

3. JShell 的前向引用 ( Forward referencing )

JShell 的前向引用 (Forward referencing) 可以让你在未定义某些方法时仍然可以调用。例如,假设我们有一个名为 greet() 的方法(如下所示)。而 greet() 内部调用了另外一个尚未定义 greetHelloWorld() 方法,这种情况下我们仍可以正确的创建 greet() 方法,但只有在 greetHelloWorld 方法创建后才可以被调用。这就是 JShell 的前向引用。

示例:

jshell> public void greet(){
...> greetHelloWorld();}
|  created method greet(), however, it cannot be invoked until method greetHelloWorld() is declared               jshell> greet()
|  attempted to call method greet() which cannot be invoked until method greetHelloWorld() is declared
jshell> public void greetHelloWorld(){
...> System.out.println("Hello World");}
|  created method greetHelloWorld()
jshell> greet()
Hello World

4. JShell 的异常处理

示例:

jshell> int divide(int a,int b) throws IOException{
...> if(b==0){
...> throw new IOException();
...> }
...> return a/b;
...> }
|  created method divide(int,int)
jshell> divide(1,0)
|  java.io.IOException thrown:
|        at divide (#2:3)
|        at (#3:1)

注意这里我们并没有捕获任何关于 divide 方法的异常,但是 JShell 会帮我们处理好。同时这里我们也没有引入 IOException 类,但代码的编译和执行都没有任何问题。原因是 JShell 的整个会话过程中会自动的引入一些常用的包,你可以使用 /imports 命令来查看 JShell 默认引用的包:

jshell> /imports
|    import java.io.*
|    import java.math.*
|    import java.net.*
|    import java.nio.file.*
|    import java.util.*
|    import java.util.concurrent.*
|    import java.util.function.*
|    import java.util.prefs.*
|    import java.util.regex.*
|    import java.util.stream.*
|    import java.io.IOException

5. JShell 会话的指令持久化行为

默认情况下 JShell 会话中的所有指令都是不被持久化的,这些指令是易失的,当用户退出 JShell 会话时就会丢失。

但是 JShell 提供了在特定的会话中保存所有指令信息的方法,你可以在另外一个新的会话中使用这些指令。当用户需要保存一些有用的代码片段时候,这个功能是很好用的。

示例:

 

jshell> String s="Hello"
s ==> "Hello"

jshell> int i=100;
i ==> 100
jshell> /save C:\data\mySession.jsh
jshell> /exit
|  Goodbye

λ jshell
|  Welcome to JShell -- Version 9.0.4
|  For an introduction type: /help intro
jshell> /vars
jshell> /open C:\Data\mySession.jsh
jshell> /vars
|    String s = "Hello"
|    int i = 100

6. 使用外部库

有很多的第三方开源库,一般开发者需要将这些库放到项目的类路径才可以使用。但是在 JShell 中,使用这些三方库更简单。

例如我们想使用 Apache Commons Lang 中的字符串工具包,可以使用如下语法来使用第三方库包:

(译者注:其实并没有那么方便)

shell> /env --class-path <Relative Path of lib from where JShell is run>
jshell> /env --class-path ../lib/commons-lang3-3.8.1.jar
|  Setting new options and restoring state.
import org.apache.commons.lang3.StringUtils;
jshell> System.out.println(StringUtils.isEmpty(""))
true
jshell> System.out.println(StringUtils.isEmpty("hello"))
false

7. 使用专门的 JShell 命令和工具来加速开发

JShell 包含很多很有用的命令,这些方法可以加速代码的测试,例如:

 /history - Prints all commands executed on JShell (Java Commands+ JShell specific commands)

示例:

jshell> String s ="Hello"
s ==> "Hello"

jshell> class Employee{
...> }
|  created class Employee

jshell> /vars
|    String s = "Hello"

jshell> /history
String s ="Hello"
class Employee{
}
/vars
/history
 /list    - Prints all JAVA related commands executed in JShell. Notice that this list the command in Numerical              order of each command identifier. This identifier can be used to execute certain construct again.

示例:

jshell> /list
1 : String s ="Hello";
2 : class Employee{
}
jshell> /1
String s ="Hello";
s ==> "Hello"
/reset   - Resets the state of current JShell session.
CTRL+R   - For searching a particular command
CTRL+S   - Performing Forward Search
CTRL+C   - To exit from JShell session
/exit    - To exit from JShell session
/vars     - To list all variables inside current JShell session
/imports  - To list all imports inside current JShell session
/help    - To know more about JShell specific commands

8. JShell 使用 Tab 键自动完成

JShell 可以使用 Tab 键来达到代码自动完成的功能。

示例:

除了这些,你还可以在 JShell 中查看相关包的文档:

jshell> java.io
io
Signatures:
java.io
<press tab again to see documentation>

9. 编辑已执行命令

在开发过程中我们经常会需要修改之前执行的命令,JShell 可以很方便的实现。

示例:

/edit        - Edit all constructs in current JShell session
/edit 1      - Edit only 1st construct (see from /list) in current JShell session
/edit Person - Edit only Person class in current JShell session

10. 如何对 JShell 扩展编程

JDK 提供 API 用来访问 JShell ,这些 API 可以浏览 JavaDoc 了解详情。

这篇文字里我们介绍了一些 JShell 的高级特性,但这并非全部,建议开发者通过 JShell 的文档了解更多信息。

文章翻译自:https://developers.redhat.com/blog/2019/04/05/10-things-developers-need-to-know-about-jshell/

© 著作权归作者所有

红薯

红薯

粉丝 21762
博文 146
码字总数 64283
作品 8
深圳
产品经理
私信 提问
加载中

评论(4)

chunkchen
chunkchen
Jupyter by Java
dwingo
dwingo
感觉用处不大
没有名字也不行?
没有名字也不行?
能不能具体列下使用场景?
lemos
lemos
good
即将改变软件开发的5个Java 9新特性

预计发布的Java 9中,最令人兴奋的特性是什么? 有关Java9的消息最近显得有些沉寂,不要被它迷惑了。JDK开发者正在努力朝着下一个版本迈进,计划2015年12月前完成所有功能开发。之后,它会经...

oschina
2015/07/22
14.9K
59
5个Java9新特性你知道了吗?

预计发布的Java 9中,最令人兴奋的特性是什么?   今天我们已经对Java 9中所期待的特性有了一个很清晰的图景。如果Java 8可以被描述为主要是lambdas表达式、streams和API变化的话,那么Jav...

Emilypz
2015/09/29
673
0
Java 10- 详解var关键字和示例教程

在本文中,我将通过示例介绍新的Java SE 10特性——“var”类型。你将学习如何在代码中正确使用它,以及在什么情况下不能使用它。 介绍 Java 10引入了一个闪亮的新功能:局部变量类型推断。对...

小刀爱编程
2018/10/12
46
0
Java 9 新特性概述

Java 9 新特性概述 成 富 2017 年 12 月 28 日发布 Java 9 正式发布于 2017 年 9 月 21 日 。作为 Java8 之后 3 年半才发布的新版本,Java 9 带 来了很多重大的变化。其中最重要的改动是 Ja...

成 富
2017/12/28
0
0
Java 9 新功能之 HTTP2 和 REPL

对Java 9的炒作将不再局限于模块化(modularity),Java 9正在搜罗大量额外的功能模块,这些功能模块正作为Java增强提案(JEP)提交,并在OpenJDK (Java SE的参考实现项目)中实现。 在这篇文...

oschina
2015/08/08
9.2K
23

没有更多内容

加载失败,请刷新页面

加载更多

小知识:讲述Linux命令别名与资源文件的区别

别名 别名是命令的快捷方式。为那些需要经常执行,但需要很长时间输入的长命令创建快捷方式很有用。语法是: alias ppp='ping www.baidu.com' 它们并不总是用来缩短长命令。重要的是,你将它...

老孟的Linux私房菜
34分钟前
2
0
《JAVA核心知识》学习笔记(6. Spring 原理)-5

它是一个全面的、企业应用开发一站式的解决方案,贯穿表现层、业务层、持久层。但是 Spring 仍然可以和其他的框架无缝整合。 6.1.1. Spring 特点 6.1.1.1. 轻量级 6.1.1.2. 控制反转 6.1.1....

Shingfi
36分钟前
4
0
Excel导入数据库数据+Excel导入网页数据【实时追踪】

1.Excel导入数据库数据:数据选项卡------>导入数据 2.Excel导入网页数据【实时追踪】:

东方墨天
44分钟前
4
1
正则表达式如何匹配一个单词存在一次或零次并且不占捕获组位置

正则表达式如何匹配一个单词存在一次或零次并且不占捕获组位置 今天要用正则表达式实现匹配一个词出现一次或者不出现的情况,但是又不仅仅是这么简单的需求。先详细说下我这种情况吧,也许有...

Airship
50分钟前
6
0
第八讲:asp.net C# web 读取文件

本讲主要讲解如何在asp.net页面上传文件。 首先,前台页面: 其次,后台页面: 结果: 1、前台效果: 2、后台结果:

刘日辉
今天
5
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部