文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day01_入门程序、常量、变量
一、数据类型
Java中的默认类型:整数类型是 int 、浮点类型是 double
//定义字节型变量
byte b = 100;
//定义短整型变量
short s = 1000;
//定义整型变量
int i = 123456;
//定义长整型变量
long l = 12345678900L;
//定义单精度浮点型变量
float f = 5.5F;
//定义双精度浮点型变量
double d = 8.5;
//定义布尔型变量
boolean bool = false;
//定义字符型变量
char c = 'A';
二、数据类型的转换
1.自动转换
int i = 1;
byte b = 2;
//int类型和byte类型运算,结果是int类型 ;如果你写成“byte x = b + i”那就会报错
int j = b + i;
int i = 1;
double d = 2.5;
//int类型和double类型运算,结果是double类型 //int类型会提升为double类型
double e = d+i;
2.自动转换的转换规则
范围小的类型向范围大的类型提升, byte、short、char 运算时直接提升为 int 。
byte、short、char‐‐>int‐‐>long‐‐>float‐‐>double
// 左边是long类型,右边是默认的int类型。一个等号代表赋值,将右侧的int常量,交给左侧的long变量进行存储。int --> long
long num1 = 100;
// float --> double,符合从小到大的规则
double num2 = 2.5F;
System.out.println(num2); // 2.5
// long --> float,符合从小到大的规则。
float num3 = 30L;
System.out.println(num3); // 30.0
3.强制转换
强制类型转换:将 取值范围大的类型 强制转换成 取值范围小的类型 。强制转换需要我们自己手动执行。
// double类型数据强制转成int类型,直接去掉小数点。
int i = (int)1.5;
// long强制转换成为int类型
int num2 = (int) 6000000000L;
// double --> int,强制类型转换
int num3 = (int) 3.99;//3
//short类型变量
short s = 1;
/*出现编译失败 s和1做运算的时候,1是int类型,s会被提升为int类型 s+1后的结果是int类型,将结果在赋值会short类型时发生错误(short内存2个字节,int类型4个字节 必须将int强制转成short才能完成赋值) */
s = s + 1;//编译失败
s = (short)(s+1);//编译成功
- byte/short/char这三种类型都可以发生数学运算,例如加法“+”. byte/short/char这三种类型在运算的时候,都会被首先提升成为int类型,然后再计算。
byte num4 = 40; // 注意!右侧的数值大小不能超过左侧的类型范围
byte num5 = 50;
// byte + byte --> int + int --> int
int result1 = num4 + num5;//90
byte num4 = 40;
short num6 = 60;
// byte + short --> int + int --> int
short result2 = (short) (num4 + num6);
三、ASCII编码
极其常用的编码
char zifu1 = '1';
System.out.println(zifu1 + 0); // 49
char zifu2 = 'A'; // 65
char zifu3 = 'c';
// 左侧是int类型,右边是char类型,char --> int,确实是从小到大,发生了自动类型转换
int num = zifu3;
System.out.println(num); // 99
四、关于自增和自减
/*
1. 在单独使用的时候,前++和后++没有任何区别。也就是:++num;和num++;是完全一样的。
2. 在混合的时候,有【重大区别】
A. 如果是【前++】,那么变量【立刻马上+1】,然后拿着结果进行使用。 【先加后用】
B. 如果是【后++】,那么首先使用变量本来的数值,【然后再让变量+1】。 【先用后加】
*/
int num1 = 10;
System.out.println(num1); // 10
++num1; // 单独使用,前++
System.out.println(num1); // 11
num1++; // 单独使用,后++
System.out.println(num1); // 12
// 与打印操作混合的时候
int num2 = 20;
// 混合使用,先++,变量立刻马上变成21,然后打印结果21
System.out.println(++num2); // 21
System.out.println(num2); // 21
int num3 = 30;
// 混合使用,后++,首先使用变量本来的30,然后再让变量+1得到31
System.out.println(num3++); // 30
System.out.println(num3); // 31
int num4 = 40;
// 和赋值操作混合
int result1 = --num4; // 混合使用,前--,变量立刻马上-1变成39,然后将结果39交给result1变量
System.out.println(result1); // 39
System.out.println(num4); // 39
int num5 = 50;
// 混合使用,后--,首先把本来的数字50交给result2,然后我自己再-1变成49
int result2 = num5--;
System.out.println(result2); // 50
System.out.println(num5); // 49
复合赋值运算符:
a += 3 相当于 a = a + 3
b -= 4 相当于 b = b - 4
c *= 5 相当于 c = c * 5
d /= 6 相当于 d = d / 6
e %= 7 相当于 e = e % 7
五、输入输出
print()方法:实现不换行的数据输出
println()方法:实现换行的数据输出
printf()方法:
%d代表十进制,%f代表浮点数,%n换行符,%s代表字符串,%c是单个字符,%%输出百分号
System.out.printf("圆的面积=%.3f",area);
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day02_API
random
Random r = new Random(); // 小括号当中留空即可
int num = r.nextInt() //得到的可能是-12354662
int num = r.nextInt(3) //实际上代表的含义是:[0,3),也就是0~2
int result = r.nextInt(n) + 1;本来范围是[0,n),整体+1之后变成了[1,n+1),也就是[1,n]
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day03_【数组、ArrayList】
一、数组
二、ArrayList
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day04_【String类、Math类】
一、字符串String
二、Math类
public class Demo01DataType {
public static void main(String[] args) {
System.out.println(Math.random()); //产生0-1之间的随机数 0.23605509569800187
System.out.println(Math.abs(-10)); //10
System.out.println(Math.max(3,6));//6
System.out.println(Math.ceil(3.1)); // 向上取整4.0
System.out.println(Math.floor(8.6)); //向下取整 8.0
System.out.println(Math.round(8.6)); //求离8.6最近的整数 9
System.out.println(Math.log(10));//求以e为底的对数,不是以10为底 2.302585092994046
System.out.println(Math.exp(2));//求e的x次方 7.38905609893065
System.out.println(Math.pow(2,3));//8.0
System.out.println(Math.sqrt(4));//2.0
System.out.println(Math.cos(3.14));//-0.9999987317275395
}
}
// 数据类型 变量名称 = 条件判断 ? 表达式A : 表达式B;
// 判断a > b是否成立,如果成立将a的值赋值给max;如果不成立将b的值赋值给max。二者选其一
int max = a > b ? a : b; // 最大值的变量
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day05_关键字【Static、this、super】
一、Static关键字
一旦使用static修饰成员方法,那么这就成为了静态方法。静态方法不属于对象,而是属于类的。
如果没有static关键字,那么必须首先创建对象,然后通过对象才能使用它。(MyClass obj = new MyClass(); obj.method();)
如果有了static关键字,那么不需要创建对象,直接就能通过类名称来使用它。(MyClass.methodStatic();)
无论是成员变量,还是成员方法。如果有了static,都推荐使用类名称进行调用。这样可读性行好,别人一看就知道它是静态的。
静态变量:类名称.静态变量
静态方法:类名称.静态方法()
二、super关键字
1.子类一定会调用父类的无参数构造方法(如果父类只有有参数的构造方法子类就不调用了)
子类构造方法当中有一个默认隐含的“super()”调用,所以一定是先调用的父类构造,后执行的子类构造。
而且super的父类构造调用,必须是子类构造方法的第一个语句。
public class Fu {
public Fu() {
System.out.println("父类的无参数构造方法!");
}
}
public class Zi extends Fu {
public Zi() {
super(); // 不管你写不写这行代码,系统都默认给你带上了
System.out.println("子类构造方法!");
}
}
2.子类必须调用父类构造方法,不写则赠送super();写了则用写的指定的super调用,super只能有一个,还必须是第一个。
public class Fu {
public Fu(int num) {
System.out.println("父类的有参数构造方法!");
}
}
public class Zi extends Fu {
public Zi() {
super(); // 不管你写不写这行代码,系统都默认给你带上了
System.out.println("子类构造方法!");
}
}
public class Demo01Constructor {
public static void main(String[] args) {
Zi zi = new Zi();
}
}
会报错,当你在子类不写super()时系统默认给你赠送了一个super()来继承父类**无参数的**构造方法,而父类只有一个**有参数**的构造方法,而你子类没有写有参数的构造方法。你改错的方法就是自己写一个super(10)来抵消掉系统给你的super()
3.super关键字的用法有三种:
- 在子类的成员方法中,访问父类的成员变量。
- 在子类的成员方法中,访问父类的成员方法。
- 在子类的构造方法中,访问父类的构造方法。
public class Zi extends Fu {
@Override
public void method() {
super.method(); // 在子类的成员方法中,访问父类的成员方法。
System.out.println("子类方法");
}
三、this关键字
this关键字用来访问本类内容。用法也有三种:
1. 在本类的成员方法中,访问本类的成员变量。
2. 在本类的成员方法中,访问本类的另一个成员方法。
3. 在本类的构造方法中,访问本类的另一个构造方法。
在第三种用法当中要注意:
A. this(...)调用也必须是构造方法的第一个语句,唯一一个。
B. super和this两种构造调用,不能同时使用。
- 在本类的成员方法中,访问本类的成员变量。
public class Zi extends Fu {
int num = 20;
public void method() {
int num = 30;
System.out.println(num); // 30,局部变量
System.out.println(this.num); // 20,本类的成员变量
System.out.println(super.num); // 10,父类的成员变量
}
}
- 在本类的成员方法中,访问本类的另一个成员方法。
public class Zi extends Fu {
public void methodA() {
System.out.println("AAA");
}
public void methodB() {
this.methodA(); //在本类的成员方法中,访问本类的另一个成员方法。
System.out.println("BBB");
}
}
- 在本类的构造方法中,访问本类的另一个构造方法。
在第三种用法当中要注意:
A. this(…)调用也必须是构造方法的第一个语句,唯一一个。
B. super和this两种构造调用,不能同时使用。
public class Zi extends Fu {
public Zi() {
this(123); // 本类的无参构造,调用本类的有参构造
}
public Zi(int n) {
this(1, 2); //在本类的构造方法中,访问本类的另一个构造方法。
}
public Zi(int n, int m) {
}
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day06_重写和重载、抽象类、接口
一、重写和重载
重写(Override):方法的名称一样,参数列表【也一样】。覆盖、覆写。
重载(Overload):方法的名称一样,参数列表【不一样】。
方法覆盖重写的注意事项:
1. 必须保证父子类之间方法的名称相同,参数列表也相同。
@Override:写在方法前面,用来检测是不是有效的正确覆盖重写。
2. 子类方法的返回值必须【小于等于】父类方法的返回值范围。
小扩展提示:java.lang.Object类是所有类的公共最高父类(祖宗类),比如你学习的java.lang.String就是Object的子类。
3. 子类方法的权限必须【大于等于】父类方法的权限修饰符。
小扩展提示:public > protected > (default) > private
4.绝大多数的,良好的编程习惯就是子类和父类的**返回值**和**权限**是相等关系
父类你写了一个method方法(父类的返回值是Sting)
public String method() {
return null;
}
子类你重写了父类的method方法(子类的返回值是Object)
@Override
public Object method() {
return null;
}
这是错误的,因为子类的返回值是Object意味着就可以是int可以是string,远大于父类给的范围
父类你写了一个method方法(父类的权限是public)
public String method() {
return null;
}
子类你重写了父类的method方法(子类的权限是private)
@Override
private String method() {
return null;
}
这是错误的,因为子类权限缩小了
二、抽象类
如何使用抽象类和抽象方法:
1. 不能直接创建new抽象类对象。
2. 子类必须覆盖重写抽象父类当中所有的抽象方法。
覆盖重写(实现):子类去掉抽象方法的abstract关键字,然后补上方法体大括号。
3. 创建子类对象进行使用。
4. 一个抽象类不一定含有抽象方法,只要保证抽象方法所在的类是抽象类,即可。
三、接口
1.接口的基本知识:
接口的名字:
接口的名字是MyInterAbstract,那么实现了这个接口的类名应该是MyInterAbstractImpl
如何定义一个接口:
public interface 接口名称 {
// 接口内容
}
注意:
1.接口的实现类必须覆盖重写(实现)接口中所有的抽象方法。(接口的快捷键Alt+Enter)
2.不能直接创建new接口对象,只能new已经实现了的接口方法
2.接口内容可以写什么呢?
- 可以写抽象方法
- 可以写抽象方法。接口当中的抽象方法,修饰符必须是两个固定的关键字:public abstract,当然,可以省略。
- 也就是说
public abstract void methodAbs1();
等价于abstract void methodAbs2();
也等价于public void methodAbs3();
还等价于void methodAbs4();
- 你在接口里面见到的
void methodAbs4();
就是public abstract void methodAbs1();
就是抽象方法
- 也可以写默认方法(见5.接口的默认方法)
- 也可以写静态方法(见6.接口的静态方法)
- 也可以写私有方法(见7.接口的私有方法)
- 也可以写常量(见8.接口的常量)
接口里面的默认方法:
public default void methodDefault() { .... }是接口中的默认方法
1.解决接口升级问题,默认的方法会被实现该接口的类继承下去。(看不懂就赶紧回去看)
2.接口中的默认方法也可以被实现类覆盖重写 public void methodDefault() { 。。。}
接口中的静态方法:
public static void methodStatic() { 。。。}是接口中的静态方法
1.不能通过接口实现类的对象来调用接口当中的静态方法。
MyInterfaceStaticImpl impl = new MyInterfaceStaticImpl();
impl.methodStatic();// 错误写法!
2.只能通过接口名称,直接调用其中的静态方法。
MyInterfaceStatic.methodStatic();//正确写法
接口中的私有方法:
1. 普通私有方法,解决多个默认方法之间重复代码问题
2. 静态私有方法,解决多个静态方法之间重复代码问题
接口中的常量:
接口的【常量】必须使用public static final三个关键字进行修饰,可以省略,也就是说接口中只有常量没有变量。
接口的私有方法
//看一下下面的啰嗦代码
public interface MyInterfacePrivateA {
public default void methodDefault1() {
System.out.println("默认方法1");
System.out.println("AAA");
System.out.println("BBB");
System.out.println("CCC");
}
public default void methodDefault2() {
System.out.println("默认方法2");
System.out.println("AAA");
System.out.println("BBB");
System.out.println("CCC");
}
}
改良后
public interface MyInterfacePrivateA {
public default void methodDefault1() {
System.out.println("默认方法1");
methodCommon();
}
public default void methodDefault2() {
System.out.println("默认方法2");
methodCommon();
}
public default void methodCommon() {
System.out.println("AAA");
System.out.println("BBB");
System.out.println("CCC");
}
}
//上述代码也有问题,你有三个public default,而public default子类是可以访问的,第三个没有必要让子类知道啊,它应该私有化
public interface MyInterfacePrivateA {
public default void methodDefault1() {
System.out.println("默认方法1");
methodCommon();
}
public default void methodDefault2() {
System.out.println("默认方法2");
methodCommon();
}
private void methodCommon() {
System.out.println("AAA");
System.out.println("BBB");
System.out.println("CCC");
}
}
3.关于接口的实现、接口的父类
1. 类与类之间是单继承的。直接父类只有一个。
2. 类与接口之间是多实现的。一个类可以实现多个接口。
3. 接口与接口之间是多继承的。
注意事项:
1. 多个父接口当中的抽象方法如果重复,没关系。
2. 多个父接口当中的默认方法如果重复,那么子接口必须进行默认方法的覆盖重写,【而且带着default关键字】。
public class MyInterfaceImpl implements MyInterfaceA, MyInterfaceB {
// 覆盖重写所有抽象方法
}
public interface MyInterface extends MyInterfaceA, MyInterfaceB {
@Override
public default void methodDefault() {
//多个父接口当中的默认方法如果重复,那么子接口必须进行默认方法的覆盖重写
}
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day07_多态、final关键字、权限修饰符、内部类
面向对象的三大特征:封装性、继承性、多态性
一、多态
1.在多态的代码当中,成员变量和成员方法的访问规则是:
成员变量:编译看左边,运行还看左边。(左边和右边指的是等号的左边和等号的右边)
成员方法:编译看左边,运行看右边。(左边和右边指的是等号的左边和等号的右边)
成员变量:编译看左边,运行还看左边。
Fu obj = new Zi()为例:编译的时候看等号左边“Fu obj”所以obj只能调用父类有的变量,obj.num是父类有的变量,但是obj.age就不行因为父类没有这个变量
运行的时候obj.num结果是多少呢?你要看的还是等号左边父类的值
成员方法:编译看左边,运行看右边。
Fu obj = new Zi()为例:编译的时候看左“Fu obj”所以obj只能调用父类有的方法和变量,obj.method()和obj.methodFu()都是父类有的方法,但是obj.methodZi()就不行因为父类没有这个方法
运行的时候obj.method()和obj.methodFu()结果是多少呢?你要看右边也就是子类
上转型和下转型
Animal animal = new Cat(); // 上转型,new Cat()就是cat的一个对象,现在把cat的一个对象new Cat()当作了Animal
Cat cat = (Cat) animal;//下转型,(Cat) animal就是把本来的猫的animal还原为Cat
instanceof的使用
如何知道这个animal是狗转过来的呢还是猫转过来的呢?用instanceof
对象 instanceof 类名称
这将会得到一个boolean值结果,也就是判断前面的对象能不能当做后面类型的实例。
public static void giveMeAPet(Animal animal) {
if (animal instanceof Dog) {
Dog dog = (Dog) animal;
dog.watchHouse();
}
if (animal instanceof Cat) {
Cat cat = (Cat) animal;
cat.catchMouse();
}
二、final关键字
final关键字代表最终、不可改变的,而且没有子孙、不能被继承。
常见四种用法:
- 可以用来修饰一个类
- 可以用来修饰一个方法
- 还可以用来修饰一个局部变量
- 还可以用来修饰一个成员变量
1.final用来修饰一个类
public final class 类名称 {
// 当前这个类不能有任何的子类。(太监类)
}
2.final用来修饰一个方法
public final 返回值类型 方法名称(参数列表) {
//这个方法就是最终方法,也就是不能被覆盖重写。
}
3.final用来修饰一个局部变量
final int num2 = 200;// 一旦使用final用来修饰局部变量,那么这个变量就不能进行更改。
四种权限修饰符
Java中有四种权限修饰符:
public > protected > (default) > private
同一个类(我自己) YES YES YES YES
同一个包(我邻居) YES YES YES NO
同一包子类(亲儿子) YES YES YES NO
不同包子类(私生子) YES YES NO NO
不同包非子类(陌生人) YES NO NO NO
注意事项:(default)并不是关键字“default”,而是根本不写,你写上default反而会报错。
什么叫做不同包子类?
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day08_Object类的toString方法、equals方法、hashCode方法
一、Object类
Object的几个常用方法:
public String toString()`:返回该对象的字符串表示。
public boolean equals(Object obj)`:指示其他某个对象是否与此对象“相等”。
Objects.equals(s1,s2)比上一个更安全,避免空指针异常
int hashCode() 返回该对象的哈希码值。
二、toString方法
1.直接打印toString()方法
//toString如果不重写打印的就是地址值
public static void main(String[] args) {
//Person类默认继承了Object类,所以可以使用Object类中的toString方法
Person p = new Person("张三",18);
String s = p.toString();
System.out.println(s);//com.itheima.demo01.Object.Person@75412c2f打印出来的是地址值
//直接打印对象的名字,其实就是调用对象的toString p=p.toString();
System.out.println(p);//com.itheima.demo01.Object.Person@5f150435打印出来的是地址值
}
2.重写toString()
Alt+Insert或鼠标右击便可以自动生成这种重写过的toString方法,不用手动重写
三、equals方法
1.直接使用equals()方法
Person类默认继承了Object类,所以可以使用Object类的equals方法
boolean equals(Object obj) 指示其他某个对象是否与此对象“相等”。object说明可以比较任何对象
基本数据类型:比较的是值
引用数据类型:比较的是两个对象的地址值
public class Demo02Equals {
public static void main(String[] args) {
Person p1 = new Person("迪丽热巴",18);
Person p2 = new Person("古力娜扎",19);
System.out.println("p1:"+p1);//p1:com.itheima.demo01.Object.Person@58ceff1
System.out.println("p2:"+p2);//p2:com.itheima.demo01.Object.Person@7c30a502
//此时p1和p2地址值不同
p1=p2;//把p2的地址值赋值给p1
boolean b = p1.equals(p2);//因为引用数据类型:==比较的是两个对象的地址值,所以地址值相同返回True
System.out.println(b);//True
}
}
2.重写equals()方法
Alt+Insert或鼠标右击便可以自动生成这种重写过的equals方法,不用手动重写!!
public class Demo02Equals {
public static void main(String[] args) {
Person p1 = new Person("迪丽热巴",18);
Person p2 = new Person("古力娜扎",19);
boolean b = p1.equals(p2);
System.out.println(b);//这样就可以比较你输入的姓名和年龄是否一样了
System.out.println(p1.equals("abc"));
}
}
四、Objects.equals(s1,s2)方法
import java.util.Objects;
public class Demo03Objects {
public static void main(String[] args) {
String s1 = "abc";
String s1 = null;
boolean b = s1.equals(s2); //会抛出空指针异常
boolean b2 = Objects.equals(s1, s2);//这就没有异常了
}
}
五、hashCode方法
1.直接使用hashCode()方法
在Object类有一个方法,可以获取对象的哈希值
int hashCode() 返回该对象的哈希码值。
public class Demo01HashCode {
public static void main(String[] args) {
//Person类继承了Object类,所以可以使用Object类的hashCode方法
Person p1 = new Person();
int h1 = p1.hashCode();
System.out.println(h1);//1967205423
//注意,有的虽然字符串不一样但是hashCode是一样的
System.out.println("重地".hashCode());//1179395
System.out.println("通话".hashCode());//1179395
}
}
2.重写hashCode方法
Alt+Insert或鼠标右击便可以自动生成这种重写过的equals方法,不用手动重写!!
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day09_时间和日期类、Calendar类
一、Date类
二、Calendar类
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day10_System类、StringBuilder、Integer
一、System类
二、StringBuilder类
三、Integer
1.装箱和拆箱
装箱:把基本类型的数据,包装到包装类中(基本类型的数据->包装类)
构造方法:
Integer(int value) 构造一个新分配的 Integer 对象,它表示指定的 int 值。
Integer(String s) 构造一个新分配的 Integer 对象,它表示 String 参数所指示的 int 值。
传递的字符串,必须是基本类型的字符串,否则会抛出异常 "100" 正确 "a" 抛异常
静态方法:
static Integer valueOf(int i) 返回一个表示指定的 int 值的 Integer 实例。
static Integer valueOf(String s) 返回保存指定的 String 的值的 Integer 对象。
拆箱:在包装类中取出基本类型的数据(包装类->基本类型的数据)
成员方法:
int intValue() 以 int 类型返回该 Integer 的值。
//装箱:把基本类型的数据,包装到包装类中(基本类型的数据->包装类)
//静态方法
Integer in3 = Integer.valueOf(1);
System.out.println(in3);//1
//Integer in4 = Integer.valueOf("a");//错误,Integer是int的箱子
Integer in4 = Integer.valueOf("1");
System.out.println(in4);//1
//拆箱:在包装类中取出基本类型的数据(包装类->基本类型的数据)
int i = in3.intValue();
System.out.println(i);//1
2.自动装箱与自动拆箱
基本类型的数据和包装类之间可以自动的相互转换
3.基本类型与字符串类型之间的相互转换
基本类型与字符串类型之间的相互转换
基本类型->字符串(String)的方法:
基本类型的值+"" 最简单的方法(工作中常用)
字符串(String)->基本类型
使用包装类的静态方法parseXXX("字符串");
Integer类: static int parseInt(String s)
Double类: static double parseDouble(String s)
//基本类型->字符串(String)
int i1 = 100;
String s1 = i1+"";
System.out.println(s1+200);//100200
//字符串(String)->基本类型
int i = Integer.parseInt(s1);
System.out.println(i-10);
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day11_Collection集合、Iterator、for each循环、泛型
一、Collection集合
Collection集合常用的功能
java.util.Collection接口
所有单列集合的最顶层的接口,里边定义了所有单列集合共性的方法
任意的单列集合都可以使用Collection接口中的方法
共性的方法:
public boolean add(E e): 把给定的对象添加到当前集合中 。
public void clear() :清空集合中所有的元素。
public boolean remove(E e): 把给定的对象在当前集合中删除。
public boolean contains(E e): 判断当前集合中是否包含给定的对象。
public boolean isEmpty(): 判断当前集合是否为空。
public int size(): 返回集合中元素的个数。
public Object[] toArray(): 把集合中的元素,存储到数组中。
//创建集合对象,可以使用多态
Collection<String> coll = new ArrayList<>();
Collection<String> coll = new HashSet<>();
//不管你创建的是ArrayList还是HashList,下面的方法都是通用的,因为我们学的是最顶层的接口Collection
System.out.println(coll);//输出为空而不是地址值,说明重写了toString方法
/*
public boolean add(E e): 把给定的对象添加到当前集合中 。
返回值是一个boolean值,一般都返回true,所以不用接收,没有意义
*/
boolean b1 = coll.add("张三");
System.out.println("b1:"+b1);//b1:true
System.out.println(coll);//[张三]
coll.add("李四");
coll.add("李四");
coll.add("赵六");
coll.add("田七");
System.out.println(coll);//[张三, 李四, 赵六, 田七]
/*
public boolean remove(E e): 把给定的对象在当前集合中删除。
返回值是一个boolean值,集合中存在元素,删除元素,返回true
集合中不存在元素,删除失败,返回false
*/
boolean b2 = coll.remove("赵六");
System.out.println("b2:"+b2);//b2:true
boolean b3 = coll.remove("赵四");
System.out.println("b3:"+b3);//b3:false
System.out.println(coll);//[张三, 李四, 田七]
/*
public boolean contains(E e): 判断当前集合中是否包含给定的对象。
包含返回true
不包含返回false
*/
boolean b4 = coll.contains("李四");
System.out.println("b4:"+b4);//b4:true
boolean b5 = coll.contains("赵四");
System.out.println("b5:"+b5);//b5:false
//public boolean isEmpty(): 判断当前集合是否为空。 集合为空返回true,集合不为空返回false
boolean b6 = coll.isEmpty();
System.out.println("b6:"+b6);//b6:false
//public int size(): 返回集合中元素的个数。
int size = coll.size();
System.out.println("size:"+size);//size:3
//public Object[] toArray(): 把集合中的元素,存储到数组中。
Object[] arr = coll.toArray();
for (int i = 0; i < arr.length; i++) {
System.out.println(arr[i]);
}
//public void clear() :清空集合中所有的元素。但是不删除集合,集合还存在
coll.clear();
System.out.println(coll);//[]
System.out.println(coll.isEmpty());//true
二、Iterator
java.util.Iterator接口:迭代器(对集合进行遍历)
有两个常用的方法
boolean hasNext() 判断集合中还有没有下一个元素,有就返回true,没有就返回false
E next() 返回迭代的下一个元素。
取出集合中的下一个元素
Iterator迭代器,是一个接口,我们无法直接使用,需要使用Iterator接口的实现类对象,获取实现类的方式比较特殊
Collection接口中有一个方法,叫iterator(),这个方法返回的就是迭代器的实现类对象
Iterator<E> iterator() 返回在此 collection 的元素上进行迭代的迭代器。
//创建一个集合对象
Collection<String> coll = new ArrayList<>();
//往集合中添加元素后coll=["姚明","科比","麦迪","詹姆斯","艾弗森",]
// 接口 实现类对象
Iterator<String> it = coll.iterator();//多态
//Iterator<E>接口也是有泛型的,迭代器的泛型跟着集合走,集合是什么泛型,迭代器就是什么泛型
while(it.hasNext()){
String e = it.next();
System.out.println(e);
}
三、for each循环
int[] arr = {1,2,3,4,5};
for(int i:arr){
System.out.println(i);
}
ArrayList<String> list = new ArrayList<>();
list.add("aaa");
list.add("bbb");
list.add("ccc");
list.add("ddd");
for(String s : list){
System.out.println(s);
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day12_数据结构、List集合、Set集合
一、List集合
java.util.List接口 extends Collection接口
List接口的特点:(有序+有索引+允许重复)
1.有序的集合,存储元素和取出元素的顺序是一致的(存储123 取出123)
2.有索引,包含了一些带索引的方法
3.允许存储重复的元素
List接口中带索引的方法(特有)
- public void add(int index, E element): 将指定的元素,添加到该集合中的指定位置上。
- public E get(int index):返回集合中指定位置的元素。
- public E remove(int index): 移除列表中指定位置的元素, 返回的是被移除的元素。
- public E set(int index, E element):用指定元素替换集合中指定位置的元素,返回值的更新前的元素。
//创建一个List集合对象
List<String> list = new ArrayList<>();//多态
//使用add方法往集合中添加元素
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.add("a");
//打印集合[a, b, c, d, a]
list.add(3,"itheima");//在c和d之间添加一个itheima现在是[a, b, c, itheima, d, a]
//public E remove(int index): 移除列表中指定位置的元素, 返回的是被移除的元素。
String removeE = list.remove(2);//返回值是c
//现在的集合是[a, b, itheima, d, a]
//public E set(int index, E element):用指定元素替换集合中指定位置的元素,返回值的更新前的元素。
String setE = list.set(4, "A");//把最后一个a,替换为A
System.out.println("被替换的元素:"+setE);//被替换的元素:a
//现在的集合是[a, b, itheima, d, A]
//List集合遍历有3种方式
//使用普通的for循环
for(int i=0; i<list.size(); i++){
String s = list.get(i);//public E get(int index):返回集合中指定位置的元素。
System.out.println(s);
}
System.out.println("-----------------");
//使用迭代器
Iterator<String> it = list.iterator();
while(it.hasNext()){
String s = it.next();
System.out.println(s);
}
System.out.println("-----------------");
//使用增强for
for (String s : list) {
System.out.println(s);
}
二、List集合的实现类
ArrayList和LinkedList实现了List
ArrayList是数组,查询快增删慢,是多线程的
LinkedList是链表,查询慢增删快,是多线程的
1.ArrayList
ArrayList的方法之前已经学过了,现在学习LinkedList
2.LinkedList集合
java.util.LinkedList集合 implements List接口
LinkedList集合里边包含了大量操作首尾元素的方法:
- public void addFirst(E e):将指定元素插入此列表的开头。
- public void addLast(E e):将指定元素添加到此列表的结尾。
- public void push(E e):将元素推入此列表所表示的堆栈。
- public E getFirst():返回此列表的第一个元素。
- public E getLast():返回此列表的最后一个元素。
- public E removeFirst():移除并返回此列表的第一个元素。
- public E removeLast():移除并返回此列表的最后一个元素。
- public E pop():从此列表所表示的堆栈处弹出一个元素。
- public boolean isEmpty():如果列表不包含元素,则返回true。
(以上是LinkedList集合特有的方法,不能使用多态)
LinkedList<String> linked = new LinkedList<>();
//使用add方法往集合中添加元素
linked.add("a");
linked.add("b");
linked.add("c");
System.out.println(linked);//[a, b, c]
linked.addFirst("www");//[www, a, b, c]
//linked.push("www"); //和上一步等价
linked.addLast("com");
System.out.println(linked);//[www, a, b, c, com]
//linked.clear();//清空集合中的元素
//public boolean isEmpty():如果列表不包含元素,则返回true。
if(!linked.isEmpty()){
String first = linked.getFirst();
System.out.println(first);
String last = linked.getLast();
System.out.println(last);
String first = linked.removeFirst();
//String first = linked.pop(); 和上一步等价
System.out.println("被移除的第一个元素:"+first);
String last = linked.removeLast();
System.out.println("被移除的最后一个元素:"+last);
三、Set集合
1.Set集合的输入和输出
java.util.Set接口 extends Collection接口
Set接口的特点:
1.不允许存储重复的元素
2.没有索引,没有带索引的方法,也不能使用普通的for循环遍历
实现了Set接口的:
java.util.HashSet集合 implements Set接口
HashSet特点:(没有索引+无序+不能存储重复的元素)
1.不允许存储重复的元素
2.没有索引,没有带索引的方法,也不能使用普通的for循环遍历
3.是一个无序的集合,存储元素和取出元素的顺序有可能不一致
4.底层是一个哈希表结构(查询的速度非常的快)
Set<Integer> set = new HashSet<>();
//使用add方法往集合中添加元素
set.add(1);
set.add(3);
set.add(2);
set.add(1);
//使用迭代器遍历set集合
Iterator<Integer> it = set.iterator();
while (it.hasNext()){
Integer n = it.next();
System.out.println(n);//1,2,3
}
//使用增强for遍历set集合
System.out.println("-----------------");
for (Integer i : set) {
System.out.println(i);
}
2.Set集合为什么不允许存储重复元素?
如果两个元素的哈希值不同,它们在set集合元素就一定认定为不同的元素。所以你想要让两个元素在set集合中相同,那么必须重写hashCode方法和equals方法才能行。
3.重写hashCode方法和equals方法
Alt+Insert系统自动添加hashCode和equals方法
import java.util.Objects;
public class Person {
private String name;
private int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Person person = (Person) o;
return age == person.age &&
Objects.equals(name, person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
public class Demo03HashSetSavePerson {
public static void main(String[] args) {
//创建HashSet集合存储Person
HashSet<Person> set = new HashSet<>();
Person p1 = new Person("小美女",18);
Person p2 = new Person("小美女",18);
Person p3 = new Person("小美女",19);
System.out.println(p1.hashCode());//734175839
System.out.println(p2.hashCode());//734175839
System.out.println(p1==p2);//地址值还是不同,因为这是两个不同的对象
System.out.println(p1.equals(p2));//True,你重写了equals方法
//只要hashCode相同,equals返回True就认定这两个元素在Set中是同一个元素
set.add(p1);
set.add(p2);
set.add(p3);
System.out.println(set);//[Person[name="小美女",age=19],Person[name="小美女",age=18]]
}
}
四、LinkedHashSet集合
java.util.LinkedHashSet集合 extends HashSet集合
LinkedHashSet集合特点:
底层是一个哈希表(数组+链表/红黑树)+链表:多了一条链表(记录元素的存储顺序),保证元素有序
public class Demo04LinkedHashSet {
public static void main(String[] args) {
HashSet<String> set = new HashSet<>();
set.add("www");
set.add("abc");
set.add("abc");
set.add("itcast");
System.out.println(set);//[abc, www, itcast] 无序,不允许重复
LinkedHashSet<String> linked = new LinkedHashSet<>();
linked.add("www");
linked.add("abc");
linked.add("abc");
linked.add("itcast");
System.out.println(linked);//[www, abc, itcast] 有序,不允许重复
}
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day13_可变参数、Collections的方法
一、可变参数
二、collections常用的方法
1.Collections.addAll()
和Collections.shuffle()
//往集合中添加多个元素的传统方法
ArrayList<String> list = new ArrayList<>();
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.add("e");
ArrayList<String> list = new ArrayList<>();
//addAll()是collections的静态方法可以直接Collections.addAll来调用
Collections.addAll(list,"a","b","c","d","e");
System.out.println(list);//[a, b, c, d, e]
//打乱顺序:打乱集合顺序。
Collections.shuffle(list);
System.out.println(list);//[b, d, c, a, e]
2.Collections.sort()
ArrayList<Integer> list01 = new ArrayList<>();
list01.add(1);
list01.add(3);
list01.add(2);
System.out.println(list01);//[1, 3, 2]
//public static <T> void sort(List<T> list):将集合中元素按照默认规则排序。
Collections.sort(list01);//默认是升序
3.Collections.sort()来自定义排序
Collections.sort()来自定义排序前提:
被排序的集合里边存储的元素,必须实现Comparable,重写接口中的方法compareTo定义排序的规则
Comparable接口的排序规则:
用自己(this)减去参数就是升序,
参数减去自己(this)就是降序
public class Person implements Comparable<Person>{
private String name;
private int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
//重写排序的规则
@Override
public int compareTo(Person o) {
//自定义比较的规则,比较两个人的年龄(this,参数Person)
//return this.getAge() - o.getAge();//用自己(this)减去参数就是升序,年龄升序排序
return o.getAge() - this.getAge();//年龄降序排序
}
}
public class Demo02Sort {
public static void main(String[] args) {
ArrayList<Person> list03 = new ArrayList<>();
list03.add(new Person("张三",18));
list03.add(new Person("李四",20));
list03.add(new Person("王五",15));
Collections.sort(list03);
System.out.println(list03);//[ Person{name='王五', age=15},Person{name='张三', age=18}, Person{name='李四', age=20}]
}
}
3.Collections.sort(List<T> list,Comparator<? super T> )
- java.utils.Collections是集合工具类,用来对集合进行操作。部分方法如下:
public static <T> void sort(List<T> list,Comparator<? super T> ):将集合中元素按照指定规则排序。
Comparator和Comparable的区别
Comparable:自己(this)和别人(参数)比较,自己需要实现Comparable接口,重写比较的规则compareTo方法
Comparator:相当于找一个第三方的裁判,比较两个
Comparator的排序规则:
o1-o2:升序
public class Student {
private String name;
private int age;
public Student() {
}
public Student(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
public class Demo03Sort {
public static void main(String[] args) {
ArrayList<Integer> list01 = new ArrayList<>();
list01.add(1);
list01.add(3);
list01.add(2);
System.out.println(list01);//[1, 3, 2]
Collections.sort(list01, new Comparator<Integer>() {
//重写比较的规则
@Override
public int compare(Integer o1, Integer o2) {
//return o1-o2;//升序
return o2-o1;//降序
}
});
System.out.println(list01);
ArrayList<Student> list02 = new ArrayList<>();
list02.add(new Student("a迪丽热巴",18));
list02.add(new Student("古力娜扎",20));
list02.add(new Student("杨幂",17));
list02.add(new Student("b杨幂",18));
System.out.println(list02);
Collections.sort(list02, new Comparator<Student>() {
@Override
public int compare(Student o1, Student o2) {
//按照年龄升序排序
return o1.getAge()-o2.getAge();
}
});
System.out.println(list02);
}
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day14_Map集合
一、Map集合
二、HashMap
java.util.Map<k,v>集合
Map集合的特点:
1.Map集合包含两个值(一个key,一个value),key和value是一一对应
实现了Map集合的接口:
java.util.HashMap<k,v>集合 implements Map<k,v>接口
HashMap集合的特点:
1.HashMap集合底层是哈希表:查询的速度特别的快
2.hashMap集合是一个无序的集合,存储元素和取出元素的顺序有可能不一致
实现了HashMap集合的接口:
java.util.LinkedHashMap<k,v>集合 extends HashMap<k,v>集合
LinkedHashMap的特点:
LinkedHashMap集合是一个有序的集合,存储元素和取出元素的顺序是一致的
put、get、remove、containsKey
//public V put(K key, V value): 把指定的键与指定的值添加到Map集合中。返回值没有意义
//public V get(Object key) 根据指定的键,在Map集合中获取对应的值。
//public V remove(Object key): 把指定的键 所对应的键值对元素 在Map集合中删除,返回被删除元素的值。
//返回值:V key存在,v返回被删除的值 key不存在,v返回null
//boolean containsKey(Object key) 判断集合中是否包含指定的键。包含返回true,不包含返回false
Map<String,Integer> map = new HashMap<>();//多态
map.put("赵丽颖",168);
map.put("杨颖",165);
map.put("林志玲",178);
System.out.println(map);//{林志玲=178, 赵丽颖=168, 杨颖=165}
Integer v1 = map.get("杨颖");
System.out.println("v1:"+v1);//v1:165
Integer v1 = map.remove("林志玲");
System.out.println("v1:"+v1);//v1:178
System.out.println(map);//{赵丽颖=168, 杨颖=165}
boolean b1 = map.containsKey("赵丽颖");
System.out.println("b1:"+b1);//b1:true
map.keySet()
Map集合的第一种遍历方式:通过键找值的方式
Map集合中的方法:
Set<K> keySet() 返回此映射中包含的键的 Set 视图。
Map<String,Integer> map = new HashMap<>();
map.put("赵丽颖",168);
map.put("杨颖",165);
map.put("林志玲",178);
Set<String> set = map.keySet();//key是字符串类型,set集合也是字符串类型
//使用迭代器遍历Set集合
Iterator<String> it = set.iterator();
while (it.hasNext()){
String key = it.next();
//3.通过Map集合中的方法get(key),通过key找到value
Integer value = map.get(key);
System.out.println(key+"="+value);
}
//使用增强for遍历Set集合
for(String key : set){
//3.通过Map集合中的方法get(key),通过key找到value
Integer value = map.get(key);
System.out.println(key+"="+value);
}
//使用增强for遍历Set集合
for(String key : map.keySet()){
//3.通过Map集合中的方法get(key),通过key找到value
Integer value = map.get(key);
System.out.println(key+"="+value);
}
entrySet()
Map集合遍历的第二种方式:使用Entry对象遍历
Map集合中的方法:
Set<Map.Entry<K,V>> entrySet() 方法名entrySet(),是返回值是Set<Map.Entry<K,V>>。
entry.getKey()获取键
entry.getValue()获取值
Map<String,Integer> map = new HashMap<>();
map.put("赵丽颖",168);
map.put("杨颖",165);
map.put("林志玲",178);
Set<Map.Entry<String, Integer>> set = map.entrySet();
//使用迭代器遍历Set集合
Iterator<Map.Entry<String, Integer>> it = set.iterator();
while(it.hasNext()){
Map.Entry<String, Integer> entry = it.next();
//3.使用Entry对象中的方法getKey()和getValue()获取键与值
String key = entry.getKey();
Integer value = entry.getValue();
System.out.println(key+"="+value);
}
//使用增强for遍历
for(Map.Entry<String,Integer> entry:set){
//3.使用Entry对象中的方法getKey()和getValue()获取键与值
String key = entry.getKey();
Integer value = entry.getValue();
System.out.println(key+"="+value);
}
三、HashMap存储自定义类型键值
HashMap存储自定义类型键值
Map集合保证key是唯一的:
作为key的元素,必须重写hashCode方法和equals方法,以保证key唯一
import java.util.Objects;
public class Person {
private String name;
private int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Person person = (Person) o;
return age == person.age &&
Objects.equals(name, person.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
}
public class Demo01HashMapSavePerson {
public static void main(String[] args) {
show02();
}
/*
HashMap存储自定义类型键值
key:Person类型
Person类就必须重写hashCode方法和equals方法,以保证key唯一
value:String类型
可以重复
*/
private static void show02() {
HashMap<Person,String> map = new HashMap<>();
map.put(new Person("女王",18),"英国");
map.put(new Person("秦始皇",18),"秦国");
map.put(new Person("普京",30),"俄罗斯");
map.put(new Person("女王",18),"毛里求斯");
//使用entrySet和增强for遍历Map集合
Set<Map.Entry<Person, String>> set = map.entrySet();
for (Map.Entry<Person, String> entry : set) {
Person key = entry.getKey();
String value = entry.getValue();
System.out.println(key+"-->"+value);
}
}
/*
HashMap存储自定义类型键值
key:String类型
String类重写hashCode方法和equals方法,可以保证key唯一
value:Person类型
value可以重复(同名同年龄的人视为同一个)
*/
private static void show01() {
//创建HashMap集合
HashMap<String,Person> map = new HashMap<>();
//往集合中添加元素
map.put("北京",new Person("张三",18));
map.put("上海",new Person("李四",19));
map.put("广州",new Person("王五",20));
map.put("北京",new Person("赵六",18));
//使用keySet加增强for遍历Map集合
Set<String> set = map.keySet();
for (String key : set) {
Person value = map.get(key);
System.out.println(key+"-->"+value);
}
}
}
三、LinkedHashMap集合
java.util.LinkedHashMap<K,V> entends HashMap<K,V>
Map 接口的哈希表和链接列表实现,具有可预知的迭代顺序。是一个有序的列表集合。
底层原理:
哈希表+链表(记录元素的顺序),是一个有序的列表集合。
public class Demo01LinkedHashMap {
public static void main(String[] args) {
HashMap<String,String> map = new HashMap<>();
map.put("a","a");
map.put("c","c");
map.put("b","b");
map.put("a","d");
System.out.println(map);// key不允许重复,无序 {a=d, b=b, c=c}
LinkedHashMap<String,String> linked = new LinkedHashMap<>();
linked.put("a","a");
linked.put("c","c");
linked.put("b","b");
linked.put("a","d");
System.out.println(linked);//{a=d, c=c, b=b} key不允许重复,有序,存和取的顺序是一致的。
}
}
四、Hashtable
java.util.Hashtable<K,V>集合 implements Map<K,V>接口
Hashtable:底层也是一个哈希表,是一个线程安全的集合,是单线程集合,速度慢
HashMap:底层是一个哈希表,是一个线程不安全的集合,是多线程的集合,速度快
HashMap集合(之前学的所有的集合):可以存储null值,null键
Hashtable集合,不能存储null值,null键
Hashtable和Vector集合一样,在jdk1.2版本之后被更先进的集合(HashMap,ArrayList)取代了
Hashtable的子类Properties依然活跃在历史舞台
Properties集合是一个唯一和IO流相结合的集合
public class Demo02Hashtable {
public static void main(String[] args) {
HashMap<String,String> map = new HashMap<>();
map.put(null,"a");
map.put("b",null);
map.put(null,null);
System.out.println(map);//{null=null, b=null}
Hashtable<String,String> table = new Hashtable<>();
table.put(null,"a");//NullPointerException
table.put("b",null);//NullPointerException
table.put(null,null);//NullPointerException
}
}
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day15_of方法、Debug追踪
一、of方法
适用于List接口,Set接口,Map接口的of方法
JDK9的新特性:
List接口,Set接口,Map接口:里边增加了一个静态的方法of,可以给集合一次性添加多个元素
static <E> List<E> of(E... elements)
使用前提:
当集合中存储的元素的个数已经确定了,不在改变时使用
注意:
1.of方法只适用于List接口,Set接口,Map接口,不适用于这些接口的实现类
2.of方法的返回值是一个不能改变的集合,集合不能再使用add,put方法添加元素,会抛出异常
3.Set接口和Map接口在调用of方法的时候,不能有重复的元素,否则会抛出异常
public class Demo01JDK9 {
public static void main(String[] args) {
List<String> list = List.of("a", "b", "a", "c", "d");
System.out.println(list);//[a, b, a, c, d]
//list.add("w");//会抛出异常,of方法的返回值是一个不能改变的集合,集合不能再使用add,put方法添加元素,会抛出异常
//Set<String> set = Set.of("a", "b", "a", "c", "d");//IllegalArgumentException:非法参数异常,有重复的元素
Set<String> set = Set.of("a", "b", "c", "d");
System.out.println(set);//[a,b,c,d]
//set.add("w");//UnsupportedOperationException:不支持操作异常
//Map<String, Integer> map = Map.of("张三", 18, "李四", 19, "王五", 20,"张三",19);IllegalArgumentException:非法参数异常,有重复的元素
Map<String, Integer> map = Map.of("张三", 18, "李四", 19, "王五", 20);
System.out.println(map);//{王五=20, 李四=19, 张三=18}
//map.put("赵四",30);//UnsupportedOperationException:不支持操作异常
}
}
二、Debug追踪
Debug调试程序:
f8:逐行执行程序
f9:跳到下一个断点,如果没有下一个断点,那么就结束程序
ctrl+f2:退出debug模式,停止程序
Console:切换到控制台
Day16_异常
由于这节内容以案例为主、且实在是太重要,不值得提炼
Day17_线程、多线程、多线程安全、线程池
由于这节内容以案例为主、且实在是太重要,浓缩后的笔记被单独摘出来
Day18_等待与唤醒机制
由于这节内容以案例为主、且实在是太重要,浓缩后的笔记被单独摘出来
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day19_Lambda表达式
Lambda表达式的标准格式:
由三部分组成:
a.一些参数
b.一个箭头
c.一段代码
格式:
(参数列表) -> {一些重写方法的代码};
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day20_File类
一、File类常用的方法
二、FileFilter文件过滤器
文章目录
- Day01_入门程序、常量、变量
- Day02_API
- Day03_【数组、ArrayList】
- Day04_【String类、Math类】
- Day05_关键字【Static、this、super】
- Day06_重写和重载、抽象类、接口
- Day07_多态、final关键字、权限修饰符、内部类
- Day08_Object类的toString方法、equals方法、hashCode方法
- Day09_时间和日期类、Calendar类
- Day10_System类、StringBuilder、Integer
- Day11_Collection集合、Iterator、for each循环、泛型
- Day12_数据结构、List集合、Set集合
- Day13_可变参数、Collections的方法
- Day14_Map集合
- Day15_of方法、Debug追踪
- Day16_异常
- Day17_线程、多线程、多线程安全、线程池
- Day18_等待与唤醒机制
- Day19_Lambda表达式
- Day20_File类
- Day21_IO流、Properties
Day21_IO流、Properties
一、字节流
- 字节输入流就是从硬盘输入到内存(读取文件内容到显示台)
- 字节输出流就是从内存写入到硬盘(写入到文件)
- 遵循“读入写出”(read方法用的是输入流,write方法用的是输出流)