平时总结知识点
JDK,JVM,JRE的解释及之间关系
JDK java开发工具包
JVM Java虚拟机
JRE Java运行时环境
JRE=JVM+运行时必须的类库 JDK=JRE+开发工具包
java程序的执行过程
由java源文件,通过javac.exe可执行文件,编译为字节码的class文件,然后通过解析器解析执行class文件,解析为计算机识别的二进制编码。
标识符在实际使用是分别对包,类,接口,变量的命名规则
- 包:全部小写,并且父级和子级文件之间使用.来分割
- 类或者接口:所有单词首字母大写。
- 方法和变量:单词首字母小写,其它后边单词首字母大写
- 常量:所有字母大写,多个单词之间用下划线连接
Java语言中定义标识符注意问题
- 标识符不能有空格;
- 标识符不能以数字开头;
- 标识符不能是java关键字;
- 不能有@、#等符号;
- Java语言大小写敏感,标识符区分大小写。
原码,反码,补码
- 原码 就是二进制定点表示法,即最高位为符号位,“0”表示正,“1”表示负,其余位表示数值的大小。
- 反码 正数的反码与其原码相同;负数的反码是对其原码逐位取反,但符号位除外。
- 补码 正数的补码与其原码相同;负数的补码是在其反码的末位加1。
java数据类型自动转换的规则
- "boolean类型不能转换成其他的数据类型
- byte、short、char之间不会互相转换,他们三者在计算时首先都会转成int类型
- 占据存储空间小的数据转换成占据存储空间大的数据可以自动转换,占据存储空间大的数据转换成占据存储空间小的数据则需要强制转换,并且会损失精度。
short s1 = 1; s1 = s1 + 1;有什么错? short s1 = 1; s1 += 1;有什么错?
- 对于short s1 = 1; s1 = s1 + 1; 由于s1+1运算时会自动提升表达式的类型,所以结果是int型,再赋值给short类型s1时,编译器将报告需要强制转换类型的错误。
- 对于short s1 = 1; s1 += 1;由于 += 是java语言规定的运算符,java编译器会对它进行特殊处理,因此可以正确编译。"
switch语句
- case后面只能是常量,不能是变量,而且,多个case后面的值不能出现相同的
- default可以省略。一般不建议。除非判断的值是固定的。
- default的位置可以出现在switch语句任意位置。
- break可以省略, 语句穿透,可以省略,一般不建议。
- switch语句的结束条件,遇到break执行到程序的末尾
if语句
- 关系表达式无论简单还是复杂,结果必须是boolean类型。
- if语句控制的语句体如果是一条语句,大括号可以省略。
- 如果是多条语句,就不能省略。建议永远不要省略。
- 一般来说:有左大括号就没有分号,有分号就没有左大括号。
while和 do while循环的区别
- while(){}//先判断是否满足循环条件,再进循环体
- do{} while();//不论条件是否满足,至少执行一次循环体
for和while的区别
- 使用上的区别
- for语句的那个控制条件变量,在循环结束后不能在使用了。而while的可以继续使用。
- 理解上的区别
- for适合于一个范围的判断。while适合次数不明确的。
三种循环语句的区别
- do…while循环至少执行一次循环体
- for和while必须先判断条件是否是true,然后后才能决定是否执行循环体
break、continue、return区别
- break用在循环或者switch中,表示退出当前判断或者退出整个循环
- continue表示跳出当前循环继续下一次循环
- return表示退出整个方法体
方法的重载(overload)
- 在同一个类中,方法名相同,参数列表不同,与返回值类型无关.
- 参数列表不同:参数类型不同;参数个数不同;参数类型顺序不同.
- 与返回值类型无关:返回值类型不同属于方法的重复定义.
数组操作常见的两个异常及场景。
- 数组索引越界:
ArrayIndexOutOfBoundsException
访问到了数组中的不存在的索引时发生。 - 空指针异常:
NullPointerException
数组引用没有指向实体,却在操作实体中的元素时。
数组的初始化方式
动态初始化:初始化时只指定数组长度,由系统为数组分配初始值。
静态初始化:初始化时指定每个数组元素的初始值,由系统决定数组长度。
匿名对象的定义及使用场景
匿名对象:就是没有名字的对象。是对象的一种简化表示形式
new 类名();
1: 当方法只调用一次时,可以使用匿名对象的写法,进行调用。
2:当实际参数为引用数据类型时,可以使用匿名对象写法,进行传递。
3:当使用链式编程时,可以使用匿名对象的写法.
static静态变量的特点
1.静态变量不会随着对象的变化而变化
2.随着类的加载而加载
3.静态变量优先于对象而存在
4.静态变量被所有该类对象所共享
5.可以使用类名直接调用,不需要使用对象名称.在不创建对象的前提下,仍然可以使用这个静态变量.建议使用类名来访问
static静态访问的注意事项
1.静态方法不能访问非静态变量
2.静态方法不能访问非静态的方法
3.静态方法中不能使用this关键字
静态变量和非静态变量的区别
- 所属不同:非静态变量属于对象,静态变量属于类,类变量
- 存储位置不同:非静态变量属于对象,所以存储在堆内存中;静态变量属于类,存储在方法区的静态区
- 生命周期不同:非静态变量属于对象,随着对象的创建而存在,随着对象的消失而消失静态变量属于类,随着类的加载而存在,随着类的消失而消失
- 访问方式不同:非静态变量只能使用对象访问;静态变量既可以使用对象访问,也可以使用类名访问
静态代码块
static{ 静态代码块内容 }
类中方法外 用于给静态的成员变量初始化赋值;用于执行那些只需要执行一次的代码
继承
关键字:extends
- 继承问题
- 私有的成员不能被继承(不能直接访问父类中的私有成员变量)
- 父类中的构造方法不能被继承(构造方法名与类名不一致),但可以调用
- 继承中成员变量关系
- 子父类中定义了不同的名称的成员变量,在子类中,既可以访问子类的成员变量,也可以访问父类的成员变量
- 子父类中定义了同名的成员变量,在子类中,根据就近原则来访问
- this和super关键字
- this表示本类当前对象的引用 super表示本类当前对象父类的引用
- this既可以访问子类中定义的成员变量,成员方法;也可以访问父类中定义的成员变量,成员方法;super只能访问父类中定义的成员变量,成员方法
- this和super都可访问构造方法 this()访问本类中其他无参构造方法,this(参数)访问本类其他有参构造;super()访问父类的无参构造方法,super(参数)访问父类有参构造
- 继承中构造方法的关系
- 在初始化子类数据之前,必须先完成对父类数据的初始化(子类可能会使用父类中的数据)
- 子类的构造方法,一定要先访问父类的构造方法
- 继承中成员方法的关系
- 在子父类中,不同名的方法: 子类可以直接调用父类的方法,也可调用子类特有方法
- 在子父类中,同名的方法: 子类重写父类方法
- 重载(overload):在同一类中,方法名相同,参数列表不同,与返回值类型无关
- 重写(override):在子父类中,方法名相同,参数列表相同,有相同的返回值类型<私有的方法不能被重写 静态的方法不能被重写>
final关键字
表示不能改变的
1.修饰变量 表示最终变量,变成了常量,只能赋值一次(能被继承)
2.修饰方法 表示最终方法,<不能被重写>
3.修饰类 表示最终类,表示不能有子类,<不能其他类重写>
多态
- 多态的前提:有子父类的继承关系 有方法的重写 父类的引用指向子类的对象
- .使用子类的引用指向子类的对象(正常情况) Zi z=new Zi();
- 使用父类的引用指向子类的对象(向上转型 小类型到大类型的转换) Fu f=new Zi();
- 让指向子类对象的父类引用,恢复成子类的引用(向下转型 大类型到小类型) Fu f=new Zi();Zi s=(Zi)f;
- 多态中成员变量(和静态方法)的访问特点: 编译看等号左边,运行看等号左边
- 多态中成员方法的访问特点: 编译看等号左边,运行看等号右边
抽象类
abstract class 类名
- 抽象方法 public abstract void 方法名(); 强制子类重写
- 抽象类中,既可以有抽象方法,也可以有一般方法;既可以有变量,也可以有常量,但不能被抽象
- 抽象类不能直接实例化,定义抽象类的子类,由子类创建对象,调用方法
接口
interface 接口名{ } Java接口中,全是方法的声明,都是抽象方法(也有一般方法但是要加default 1.8新特性)
实现接口class 类名 implements 接口名{ }
- 接口不能直接实例化,定义实现类,实现接口,由实现类创建对象,调用方法
- 接口中,方法只有抽象方法,成员变量只有常量,没有构造方法(实现类访问的是父类构造 父类是亲爹,接口是干爹)
- 类与类、类与接口、接口与接口’
- 类与类: 继承关系(extends),单继承
- 类与接口: 实现关系(implements),单实现,多实现 class 实现类类名 implements 接口1,接口2…{ }
- 继承的前提下,还可实现多个接口 class 子类类名 extends 父类 implements 接口1,接口2…{ }
- 接口与接口: 继承关系 interface 接口名 extends 父接口1,父接口2…{ }
普通类、抽象类、接口
内部类
- 静态内部类: 访问方式: 外部类名.内部类名 内部类对象名 = new 外部类名.内部类名();
- 非静态内部类:
- 普通成员内部类: 访问方式: 外部类名.内部类名 内部类对象名 = new 外部类名().new 内部类名();
- 私有成员内部类: 访问方式:在外部类中定义一个访问私有成员内部类的公有方法
- 局部内部类: 定义在方法里面,在这个方法里面创建对象访问
- 匿名内部类: 没有名字的内部类 继承一个类;实现一个接口 new 父类或接口名称(){…};
方法只使用一次,不需要定义实现类或子类
代码块
权限修饰符
- private 只能被本类中被访问
- 默认 可以在本类中被访问 可以在本包中的其他类中被访问
- protected 可以在本类中被访问 可以在本包中的其他类中被访问 可以在其他包的子类中被继承
- public 可以在本类中被访问 可以在本包中的其他类中被访问 可以在其他包的子类中被继承 其他包中的无关类中被访问
Object类型
所有类型的父类
- getClass()方法: 返回当前对象的运行时类 class 全类名
- getName()方法: 返回当前类型的全类名
- hashCode()方法: 返回对象的哈希码值
- toString()方法: 返回当前对象的字符串表示
- 全类名+@+哈希码值的十六进制表示 getClass().getName()+"@"+Integer.toHexString(hashCode());
==和equals()
都是用于比较数据是否相等的方式
==可以比较基本数据类型, 也可以比较引用数据类型; equals()只能比较引用数据类型;
==在比较基本数据类型的时候, 比较的是数据的值; 比较引用数据类型时,比较的是数据的地址值;
equals()方法在重写之前,比较的是两个对象的地址值; 在重写之后, 比较的是两个对象的属性值。
Scanner
扫描器,可以扫描指定设备的基本数据类型和字符串
构造方法: Scanner(File f):扫描指定文件
Scanner(String path):扫描指定的路径
Scanner(InputStream is):扫描指定的输入流
System.in:标准的输入流,默认关联到键盘 InputStream is = System.in; Scanner sc = new Scanner(is);
基本方法: 没有nextChar这个方法
System类 System.currentTimeMillis();返回当前时间的毫秒值
String
不可变字符序列
构造方法:
String() 创建一个空字符串 ""(不是null)
String(String str) 初始化一个str字符串
String(byte[] brr) 将字节数组转成一个字符串
String(byte[] brr,int 起始索引,int 长度) 将字节数组的一部分转成字符串
String(char[] brr) 将字符数组转成一个字符串
String(char[] brr,int 起始索引,int 长度) 将字符数组的一部分转成字符串
String类型的判断方法:
equals()
equalsIgnoreCase(String str): 忽略大小写判断两个字符串的内容是否相等
contains(String str): 判断是否包含str
startsWith(String str): 判断是否以str开头
endsWith(String str): 判断是否以str结尾
isEmpty(): 判断是否是空串
String类型的获取方法:
length)():获取字符串的个数 有括号()这是个方法
charAt(int index)
substring(int beginIndex)
substring(int beginIndex,int endIndex)
indexOf(a): 返回a在字符串中第一次出现的索引
indexOf(a,int from): 从from开始寻找,a第一次出现的索引
lastIndexOf: 和indexOf一样,只不是是从后往前找, 但是索引不会变化
String类型的转换方法:
getByte(): 将字符串转为字节数组
toCharArray(): 将字符串转为字符数组
String.valueOf(a): 将任意类型转为字符串
String类型的其他方法:
replace(String old,String new): 将老串全部替换成新串
trim(): 去掉两端的空格,制表符
StringBuilder
可变的字符序列
构造方法:
StringBuilder():创建一个生成器,初始容量为16个字符
StringBuilder(int num):创建一个生成器,初始容量为num大小
StringBuilder(String str): 创建一个生成器,初始值为str,初始大小为str+16
获取容积的方法:
capatity(): 获取当前生成器的容器大小
length(): 获取当前生成器中的字符个数
添加方法:
append(任意):添加任意
insert(int index,任意): 添加任意到指定位置
删除方法:
deleteCharAt(int index): 删除指定索引的字符
delete(int start,int end): 删除指定范围的字符
替换反转:
replace(int start,int end,String new):将start到end的替换成new
reverse():将字符序列反转
int类型和String类型转换
int —> String Stirng str = String.valueOf(int a);
String —> int int a = Integer.parseInt(String str);
正则表达式
字符类:[]
[abs]: a或b或s中的一个
[^abs]:除了a,b,s以外的任何单个字符
[a-zA-Z]:a-z,A-Z中的任意单个字符
预定义字符类:
. 表示任意字符
\d 表示数字字符
\D 表示非数字字符
\s 表示空格,制表符,换行
\W 表示非空格字符
\w [a-zA-Z0-9]
\W 表示除了\w以外的所有字符
数量词:
X? 表示X这个字符,出现0次或者1次
X+ 表示X这个字符,出现1次或者多次
X* 表示X这个字符,出现0次,1次或多次
X{n} 表示X这个字符,恰好出现n次
X{n,} 表示X这个字符,至少出现n次
X{n,m} 表示X这个字符,至少出现n次,最多出现m次
boolean match(String regex): 判断当前字符串是否和参数正则表达式匹配
String[] split(String regex): 使用指定的正则表示式切割当前字符串
泛型
提高的数据的安全性,将运行时的问题,提前暴露在编译时期 避免的强转的麻烦
前后一致:
声明引用的类型的泛型,必须和创建对象的类型的泛型一致(一模一样,不能有子父类关系)
菱形泛型:
前面声明引用的泛型写好之后,后面创建对象使用的泛型可以不写(尖括号必须加上,像菱形,称为“菱形泛型”,jdk1.7之后)
泛型类:带着泛型定义的类
格式:class 类名<泛型类型1, 泛型类型2, 泛型类型3....> {
}
泛型的确定时机:创建对象的时候才能确定
泛型方法:带着泛型声明的方法
格式: 修饰符 <泛型类型1, 泛型类型2...> 返回值类型 方法名称(参数列表) {
}
泛型类上的泛型,是在创建对象的时候确定的,所以:
【非静态】方法,可以直接使用类上声明的泛型
【静态】方法,可以在创建对象之前,调用,所以不能使用类上声明的泛型,如果静态方法需要使用泛型,必须声明自己特有的泛型
泛型接口:带着泛型定义的接口
格式:interface 接口名称 <泛型类型1, 泛型类型2...> {
}
实现类的两种情况:
1、实现类不是一个带泛型的类,泛型类型已经被确定了,如下:
class 实现类类名 implements 接口名称<具体的已知类型> {
}
2、实现类还是一个带泛型的类,泛型类型和接口的泛型一致,格式:
class 实现类类名<泛型声明符号1> implements 接口名称<泛型声明符号1> {
}
Comparator《T》接口
泛型:表示这个比较器可以比较的数据类型
有一个抽象方法,可以让我们去定义两个参数究竟谁大
int compare(T o1, T o2)
1、返回值的规则:
返回正数,表示o1大于o2,将来o1存储在o2的后面
返回负数,表示o1小于o2,将来o1存储在o2的前面
返回0,表示o1等于o2
2、参数的规则:
o1,表示即将存储到数组中的元素
o2,表示已经存在于数组中的元素
Collection集合
集合和数组的区别:
共同点:都是用于存储数据的容器
不同点: 存储内容不同: 数组既可以储存基本数据类型, 也可以储存引用数据类型
存储数量不同: 数组的长度不可变, 一旦确定大小就无法增删
集合的长度可变,是一个可伸缩的容器
方法不同: 数组中只有Object中定义的方法, 以及有一个length属性
集合中可以有很多方法
Collection: 单列集合的顶层接口
常用方法:
add(Object obj)
remove(Object obj)
clear()
isEmpty()
contains(Object obj)
size()
转数组: Object[] obj = c.toArray();
带all的方法:
addAll(Collection c);
removeAll(Collection c);
containsAll(Collection c);
retainAll(Collection c);取交集
List: Collection的一个子接口 有序,有索引,可以重复
特有方法:
add(int index,Object obj)
remove(int index)
set(int index,Object obj)
get(int index)
List的实现类:
ArrayList 数组实现,顺序存储 查询修改快,增删慢
LinkedList 节点实现,链式存储 查询修改慢,增删快
LinkedList特有方法:
addFirst(Object obj)
addLast(Object obj)
removeFirst()
removeLast()
getFirst()
getLast()
Set: Collection的一个子接口 无序,没有索引,不可以重复
1、没有特有的遍历方式,全都使用Collection中的遍历方式
2、4种遍历方式:
转成不带泛型的数组
转成带泛型的数组
使用迭代器
增强for循环
转数组不带泛型: 1、Object[] toArray() 无论集合是否带泛型的,返回的都是Object[]
转数组带泛型: T[] toArray(T[] arr) 带泛型的转数组,得到的是T类型的数组
1、参数数组的容量较小,集合中元素个数较多,就会在方法内部生成一个新的数组,装集合中的元素,将新数组返回
2、参数数组的容量较大,集合中元素个数较少,就不需要创建新的数组,返回的数组和参数数组是同一个数组。空余的空间,使用null填充
3、参数数组的容量和集合元素个数一样多,就不需要创建新数组,返回的数组和参数数组是同一个数组。没有剩余空间。
HashSet
LinkedHashSet 是HashSet的一个子类,和HashSet保证元素唯一性的原理相同
既保证年元素的唯一,又保证原来的顺序
Map集合
-
双列集合的顶层接口 描述的是一个数据(key)到另一个数据(value)的映射关系
特点: Key键是唯一的, value值不是唯一的 Map中的所有操作和算法都是针对键 有效的, Collection中的Set子接口中的操作和算法针对元素有效 -
Map中常用的方法
增加(修改)键值对: put(K key, V value)
删除给定键的键值对: remove(K key)
清空集合: clear()
获取集合的大小: size()
获取给定键的对应值: get(K key)
判断集合中是否存在某个键: containsKey(Object obj)
判断集合中是否存在某个值: containsValue(Object obj) -
Map集合的遍历方式
- 第一种: 根据键获取值
获取Map集合中的所有键,放到一个Set集合中去,遍历该Set集合,获取到每一 个键,根据键再来获取对应的值
Set set = map.kenySet(); 迭代器 foreach循环 - 第二种: 根据键值对对象获取键和值
获取Map集合中所有的键值对对象(Entry) , 到Set集合中, 遍历Set集合, 拿 到的是每个键值对对象(Entry) , 从这个对象中分别获取键和值
Set<Map.Entry<K,V>> set = map.entrySet();
getKey() : 获取当前键值对对象的键
getValue() : 获取当前键值对对象的值
- 第一种: 根据键获取值
length
- 数组中length是属性, 后面不加括号()
- String中length是方法 , 后面所以加括号()
- 集合是size() , 不是length
File类
-
绝对路径: 从根目录开始的路径, 称为绝对路径
相对路径: 相对于某个路径而言的路径 -
File类型的构造方法:
File(String path) 把字符串路径封装成一个File对象
File(String parent, String child) 将两个字符串(父级路径,子级路径)拼接之后形成的路径,封装成File对象
File(File parent , String child) 将File类型的父级路径和String类型的字节路径拼接成一个新路径,封装成File对象创建好File对象之后,只是封装了一个路径,和磁盘上是否有这个路径,无关
-
创建文件:
createNewFile() -
创建文件夹:
mkdir()
创建文件夹,如果父级路径不存在,则文件夹创建失败
mkdirs()
创建文件夹,如果父级路径不存在,则自动创建父级路径,再创建子级路径 -
删除方法:delete()
既可以删除文件,也可以删除文件夹
1、删除的时候不走回收站,直接删除
2、不能删除非空文件夹 -
重命名方法renameTo(File dest)
注意事项:
1、方法的调用者,是一个File对象,方法的参数是另外一个File对象
2、调用者是当前修改之前的路径对象,参数是要修改为的路径对象
3、如果改了父级路径,就是剪切,如果不改父级路径就是重命名 -
判断功能:
exists(),判断调用者路径是否存在
isFile(),判断调用者是否是一个文件
isDirectory(),判断调用者是否是一个文件夹 -
获取方法
1、获取路径三个方法:
getName()
获取最短的那个文件或者文件夹名称
getPath()
获取相对路径,构造方法中传入的那个字符串
getAbsolutePath()
获取绝对路径
2、获取文件或者文件夹属性的方法
length()
获取文件的字节个数
只能针对文件使用,不能针对文件夹使用
lastModified()
获取文件的最后修改时间
3、获取文件夹中内容的方法
String[] list()
返回文件夹中的所有内容的名称(不包含子文件夹中的内容)
File[] listFiles()
返回文件夹中的所有内容的File对象(不包含子文件夹中的内容)
注意事项:
这两个方法只能针对文件夹使用,不能针对文件使用
(待更新)