「Java」程序基础
程序基本结构
因为Java是面向对象的语言,一个程序的基本单位就是class,class是关键字
1 | public class Hello { // 类名是Hello |
类名要求:
- 类名必须以英文字母开头,后接字母,数字和下划线的组合
- 习惯以大写字母开头
在class内部,可以定义若干方法。方法定义了一组执行语句,方法内部的代码将会被依次顺序执行。
Java入口程序规定的方法必须是静态方法,方法名必须为main,括号内的参数必须是String数组。
方法命名要求:
- 首字母小写
Java的每一行语句必须以分号结束
注释:和c语言一样
还有一种特殊的多行注释,以/**开头,以*/结束,如果有多行,每行通常以星号开头:
1 | /** |
这种特殊的多行注释需要写在类和方法的定义处,可以用于自动创建文档。
变量 && 数据类型
变量的默认值总是0, 使用方法和C语言相同。
基本数据类型是CPU可以直接进行运算的类型。Java定义了以下几种基本数据类型:
- 整数类型:byte,short,int,long
- 浮点数类型:float,double
- 字符类型:char
- 布尔类型:boolean
计算机内存的最小存储单元是字节(byte),一个字节就是一个8位二进制数,即8个bit。 换算成十进制是0
255,换算成十六进制是00ff。
基本数据类型占用的字节数:
1 | ┌───┐ |
整型
各种整型能表示的最大范围如下:
- byte:-128 ~ 127
- short: -32768 ~ 32767
- int: -2147483648 ~ 2147483647(10位)
- long: -9223372036854775808 ~ 9223372036854775807
1 | long l = 9000000000000000000L; // long型的结尾需要加L |
注意:同一个数的不同进制的表示是完全相同的,例如15=0xf=0b1111。
浮点型
因为小数用科学计数法表示的时候,小数点是可以“浮动”的,如1234.5可以表示成$ 12.345\times10^2 $,也可以表示成$ 1.2345\times10^3 $ ,所以称为浮点数。
1 | float f1 = 3.14f; // float类型,需要加上f后缀。 |
float类型可最大表示$3.4\times10^{38}$,而double类型可最大表示$1.79\times10^{308}$。
布尔类型
1 | boolean b1 = true; |
字符类型
字符类型char表示一个字符。Java的char类型除了可表示标准的ASCII外,还可以表示一个Unicode字符
**注意char类型使用单引号',且仅有一个字符,要和双引号"的字符串类型区分开。 **
引用类型
除了上述基本类型的变量,剩下的都是引用类型。例如,引用类型最常用的就是String字符串:
1 | String s = "hello"; |
引用类型的变量类似于C语言的指针,它内部存储一个“地址”,指向某个对象在内存的位置
输出某个位置的字符:
1 | System.out.println(str.charAt(i)) |
常量
定义变量的时候,如果加上final修饰符,这个变量就变成了常量:【 常量名通常全部大写 】
1 | final double PI = 3.14; // PI是一个常量 |
字符和字符串
因为Java在内存中总是使用Unicode表示字符,所以,一个英文字符和一个中文字符都用一个char类型表示,它们都占用两个字节。要显示一个字符的Unicode编码,只需将char类型直接赋值给int类型即可。
还可以直接用转义字符\u+Unicode编码来表示一个字符:
1 | // 注意是十六进制: |
字符串类型String是引用类型,我们用双引号"..."表示字符串。
注意要区分空值null和空字符串"",空字符串是一个有效的字符串对象,它不等于null。
字符串连接
可以使用+连接任意字符串和其他数据类型,这样极大地方便了字符串的处理。 如果用+连接字符串和其他数据类型,会将其他数据类型先自动转型为字符串,再连接 。
从Java 13开始,字符串可以用"""..."""表示多行字符串(Text Blocks):
1 | String s = """ |
如果多行字符串的排版不规则,那么总是以最短的行首空格为基准。
最后,由于多行字符串是作为预览特性(Preview Language Features)实现的,编译的时候,我们还需要给编译器加上参数:
1 | javac --source 14 --enable-preview Main.java |
字符串数组
1 | String[] names = { |
$var$ 关键字
如果类型名字太长写起来会比较麻烦,如果想省略变量类型可以使用var关键字:
1 | StringBuilder sb = new StringBuilder(); |
数组
1 | int[] ns = new int[5]; |
多维数组
1 | int[][] ns = { |
1 | int[][][] ns = { |
运算
整数除法的结果只保留整数部分。
+=,-=,*=,/= ,++,-- 这些运算操作Java都有。
类型自动提升与强制转型
在运算过程中,如果参与运算的两个数类型不一致,那么计算结果为较大类型的整型。例如,short和int计算,结果总是int,原因是short首先自动被转型为int
1 | int i = 12345; |
溢出
整数运算在除数为0时会报错,而浮点数运算在除数为0时,不会报错,但会返回几个特殊值:
NaN表示Not a NumberInfinity表示无穷大-Infinity表示负无穷大
输入和输出
println是print line的缩写,表示输出并换行。因此,如果输出后不想换行,可以用print()
1 | System.out.print(".."); |
格式化输出
如果要把数据显示成我们期望的格式,就需要使用格式化输出的功能。格式化输出使用System.out.printf(),通过使用占位符%?,printf()可以把后面的参数格式化成指定格式
1 | double d = 3.1415926; |
输入
一个从控制台读取一个字符串和一个整数的例子:
1 | import java.util.Scanner; |
System.out代表标准输出流,而System.in代表标准输入流。直接使用System.in读取用户输入虽然是可以的,但需要更复杂的代码,而通过Scanner就可以简化后续的代码。
有了Scanner对象后,要读取用户输入的字符串,使用scanner.nextLine(),要读取用户输入的整数,使用scanner.nextInt()。Scanner会自动转换数据类型,因此不必手动转换。
输入字符串 遇到空格或者换行结束 :
1 | Scanner sc=new Scanner(System.in); |
输入一行字符串,可以包括空格:
1 | Scanner sc=new Scanner(System.in); |
判断
1 | if (条件) { |
判断值类型的变量是否相等,可以使用==运算符。但是,判断引用类型的变量是否相等,==表示“引用是否相等”,或者说,是否指向同一个对象。
1 | String s1 = "hello"; |
要判断引用类型的变量内容是否相等,必须使用equals()方法:
1 | if (s1 != null && s1.equals(s2)) { // 避免NullPointerException错误 |
switch
1 | String fruit = "apple"; |
从Java 12开始,switch语句升级为更简洁的表达式语法,使用类似模式匹配(Pattern Matching)的方法,保证只有一种路径会被执行,并且不需要break语句:
1 | String fruit = "apple"; |
还可以直接返回值:
1 | String fruit = "apple"; |
如果需要复杂的语句,我们也可以写很多语句,放到{...}里,然后,用yield返回一个值作为switch语句的返回值:
1 | String fruit = "orange"; |
循环
1 | while (条件表达式) { |
1 | do { |
1 | for (初始条件; 循环检测条件; 循环后更新计数器) { |
命令行参数
Java程序的入口是main方法,而main方法可以接受一个命令行参数,它是一个String[]数组。
这个命令行参数由JVM接收用户输入并传给main方法:
1 | public class TestArgs { |
命令行执行:
1 | $ javac Main.java |
如果是vsc的话已经生成了.class文件,就无需第一行命令了。