读书笔记《写给大忙人的JavaSE 9 核心技术》
第一章 基本的编程结构
关于Java用途的定义
Java 不是用来快速完成几个命令的脚本语言,它明确定位为可以从组织有序的类和包以及模块中获益的大型程序的编程语言
JShell
Java 9中引入的运行Java语句的交互式命令窗口,和Python Node差不多。
基本类型
8种基本类型
有符号整型
类型 | 存储需求 |
---|---|
byte | 1个字节 ( -128–127) |
short | 2个字节 (-32768–32767) |
int | 4个字节 (约20亿) |
long | 8个字节 (约9千亿亿) 2的63次方 |
如果long类型还不够用,可以使用BigInteger类
- 0x 是16进制前缀
- 0b是2进制前缀
tips:为了方便阅读,可以在数字中间加上下划线,1_000_0000,编译时会自动删除掉。
浮点类型
类型 | 存储需求 |
---|---|
float | 4个字节 (6-7位有效小数) |
double | 8个字节 (15位有效小数) |
对于float来说,4个字节,32位,0-22位表示尾数,23-30(8位)表示指数,31位表示符号位。
对于double来说,8个字节,64位,0-51表示尾数,52-62(11位)表示指数,63位最高位表示符号位。
浮点数不适合做金融计算
java
2.0-1.1 = 0.89999999999
二进制表示浮点数有些数字是没办法精确表示的。
如果要精准无误的表示应使用 BigDecimal
char 类型
JAVA中,char占2字节,16位。可在存放汉字
- char a='a'; //任意单个字符,加单引号。
- char a='中'; //任意单个中文字,加单引号。
- char a=111; //整数。0~65535。十进制、八进制、十六进制均可。输出字符编码表中对应的字符。
注:只能放单个字符。
布尔类型
true false
关于字符集、字符编码
Unicode
Unicode 是为了解决传统的字符编码方案的局限而产生的,它为每种语言中的每个字符设定了统一并且唯一的二进制编码,以满足跨语言、跨平台进行文本转换、处理的要求。
Unicode通常用两个字节表示一个字符,原有的英文编码从单字节变成双字节,只需要把高字节全部填为0就可以。
ASCII
一个字节能表示的最大的整数就是255(二进制11111111=十进制255),0 – 255被用来表示大小写英文字母、数字和一些符号,这个编码表被称为ASCII编码,比如大写字母A的编码是65,小写字母z的编码是122。
GB2312
如果要表示中文,显然一个字节是不够的,至少需要两个字节,而且还不能和ASCII编码冲突,所以,中国制定了GB2312编码,用来把中文编进去。
参考资料:
strictfp
关键字strictfp是strict float point的缩写,指的是精确浮点,它是用来确保浮点数运算的准确性,JVM在执行浮点数运算时,如果没有指定strictfp关键字,此时计算结果可能会不精确,而且计算结果在不同平台或厂商的虚拟机上会有不同的结果,导致意想不到的错误。
而一旦使用了strictfp来声明一个类、接口或者方法,那么在所声明的范围内,Java编译器以及运行环境会完全依照IEEE二进制浮点数算术标准来执行,在这个关键字声明的范围内所有浮点数的计算都是精确的。
需要注意的是,当一个类被strictfp修饰时,所有方法都会自动被strictfp修饰。
因此,strictfp可以保证浮点数运算的精确性,而且在不同的硬件平台会有一致的运行结果。
public strictfp class Test {
int a = 1;
public static void testStrictfp(){
float f = 0.12365f;
double d = 0.03496421d;
double sum = f + d;
System.out.println(sum);
}
public static void main(String[] args) {
testStrictfp();
}
}
运行结果:0.15861420949932098
字符串
字符串不是基本类型,字符串是对象!
字符串连接
将几个字符以分隔符连接起来,可以使用join()方法,
String names = String.join("-","Peter","Paul","Mary")
在操作大量字符串时,使用StringBuilder 效率更高
字符串截取
String w = "Hellow,World";
w.substring(7,12);// 开始位置,结束位置(不包含)
字符串比较相等
w.equals("World")
//是比较在内存中是否是一个对象,而不是字面量
w == "World"
// 不考虑大小写比较字符串
w.equalsIgnoreCase("World")
数字转字符串
Integer.toString(number,n)// number要转换的数字,n:基数,就是几进制,不传默认十进制
//最简便的方法 数字加空串
number+""
字符串转数字
Integer.parseInt()
Double.parseDouble()
读取输入
System.in对象只能读取单个字节的方法,要读取字符串和数字,需要构造一个依附到System.in的Scanner
Scanner in = new Scanner(System.in)
String s = in.nextLine()
if(in.hasNextInt()){
int age = in.nextInt()
}
//读取密码是可以只用Console类
Console terminal = System.console()
String s = terminal.readLine("user name");
char[] pasw = terminal.readPassword("Password");
shell 重定向
输入输出到文件
java mypackage.MainClass<input.txt> output.txt
此时System.in从input.txt中读取,System.out将会输出到output.txt
循环
break 跳出整个循环
continue 跳出此次循环
数组和数组列表
数组定长不可变
String[] myStringArr = nwe String[100]
构造数组时Java会默认填充数组,
- 数字类型、char类型 用0填充
- boolean 用 false 填充
- 对象数组用null填充
数组列表较为灵活
ArrlyList对象在内部管理数组。数组不够用时会自动创建另外一个内部数组,并且将元素移动到该数组。这个过程对程序员透明。
数组列表是泛型类,泛型类不能使用基本类型作为类型参数,要用基本类型的包装类。
ArrayList<int> //错误
ArrayList<Integer>//正确
- Integer
- Byte
- Short
- Long
- Character
- Float
- Double
- Boolean
增强型for循环
int[] numbers = new int[10]
for(int n : numbers){
sum += n
}
此时的循环变量不是索引值,而是索引对应的值。
数组与数组列表的复制
int[] numbers = new int[10]
int[] myNums = numbers
此时numbers,myNums这两个变量引用同一个数组对象,也就是这两个变量共享一个数组,利用numbers进行操作,myNums也会变。JavaScript中也是这样!
int copys = Arrays.copyof(numbers,numbers.length)
//friends为已有的数组列表
ArrayList<String> copys = new ArrayList<>(friends)
命令行参数
java test.java -name merry -p 3306
-name merry -p 3306 这四个字符串会封装成一个字符串数组传递给main函数
public static main(String[] args)