jdk1.8新特性
HashMap在1.7中使用的数组+链表的组合形式,在jdk1.8中采用的是数组+链表+红黑树组成的。
- Lambda表达式
老版的字符串排序
List<String> names = Arrays.asList("zhangsan", "lisi", "wangwu", "zhaoliu");
Collections.sort(names, new Comparator<String>() {
@Override
public int compare(String a, String b) {
return b.compareTo(a);
}
});
而通过Lambda表达式的排序则更加简便,不需要再在其中实现内部匿名类
Collections.sort(names,(String a,String b) ->{
return b.compareTo(a);
});
编译器可以自动推导出参数类型,所以可以不写类型,当代码只有一行的时候,还可以直接省略return关键字和{}
Collections.sort(names,( a, b) -> b.compareTo(a));
-
接口的默认方法
jdk1.8之后新增了接口的默认方法。简单说,默认方法就是接口可以有实现方法,而且不需要实现类去实现其方法。我们只需在方法名前面加个 default 关键字即可实现默认方法。为什么要有这个特性?
首先,之前的接口是个双刃剑,好处是面向抽象而不是面向具体编程,缺陷是,当需要修改接口时候,需要修改全部实现该接口的类,目前的 java 8 之前的集合框架没有 foreach 方法,通常能想到的解决办法是在JDK里给相关的接口添加新的方法及实现。然而,对于已经发布的版本,是没法在给接口添加新方法的同时不影响已有的实现。所以引进的默认方法。他们的目的是为了解决接口的修改与现有的实现不兼容的问题。
示例代码如下:
public class Dome {
public static void main(String[] args) {
Dome1 dome=new Dome3();
dome.print();
}
}
interface Dome1{
default void print() {
System.out.println("接口Dome1的默认方法");
}
static void blowHorn() {
System.out.println("接口Dome1的静态方法");
}
}
interface Dome2{
default void print() {
System.out.println("接口Dome2的默认方法");
}
}
class Dome3 implements Dome1,Dome2{
@Override
public void print() {
// TODO Auto-generated method stub
Dome1.super.print();
Dome2.super.print();
Dome1.blowHorn();
System.out.println("实现类方法");
}
}
运行结果
接口Dome1的默认方法
接口Dome2的默认方法
接口Dome1的静态方法
实现类方法
-
日期时间API
Java 8 在 java.time 包下提供了很多新的 API。以下为两个比较重要的 API:Local(本地) − 简化了日期时间的处理,没有时区的问题。
Zoned(时区) − 通过制定的时区处理日期时间。
新的java.time包涵盖了所有处理日期,时间,日期/时间,时区,时刻(instants),过程(during)与时钟(clock)的操作
代码实现
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.Month;
public class Dome {
public static void main(String args[]){
Dome java8tester = new Dome();
java8tester.testLocalDateTime();
}
public void testLocalDateTime(){
// 获取当前的日期时间
LocalDateTime currentTime = LocalDateTime.now();
System.out.println("当前时间: " + currentTime);
LocalDate date1 = currentTime.toLocalDate();
System.out.println("date1: " + date1);
Month month = currentTime.getMonth();
int day = currentTime.getDayOfMonth();
int seconds = currentTime.getSecond();
System.out.println("月: " + month +", 日: " + day +", 秒: " + seconds);
LocalDateTime date2 = currentTime.withDayOfMonth(05).withYear(2019);
System.out.println("date2: " + date2);
LocalDate date3 = LocalDate.of(2019, Month.SEPTEMBER, 05);
System.out.println("date3: " + date3);
// 22 小时 15 分钟
LocalTime date4 = LocalTime.of(22, 58);
System.out.println("date4: " + date4);
// 解析字符串
LocalTime date5 = LocalTime.parse("22:58:30");
System.out.println("date5: " + date5);
}
}
运行结果
当前时间: 2019-09-05T23:03:00.414
date1: 2019-09-05
月: SEPTEMBER, 日: 5, 秒: 0
date2: 2019-09-05T23:03:00.414
date3: 2019-09-05
date4: 22:58
date5: 22:58:30
-
方法引用
方法引用通过方法的名字来指向一个方法。方法引用可以使语言的构造更紧凑简洁,减少冗余代码。
方法引用使用一对冒号 :: 。
其中的方法引用可以如下所使用
public class Dome {
public static void main(String[] args) {
List names = new ArrayList();
names.add("Zhangsan");
names.add("Lisi");
names.add("Wangwu");
names.add("Zhaoliu");
names.add("Sunqi");
//names.forEach(System.out::println);
for (Object object : names) {
System.out.println(object);
}
}
}
其中names.forEach(System.out::println);这条语句与其中的for循环打印结果都如下所示
Zhangsan
Lisi
Wangwu
Zhaoliu
Sunqi
看完了上边的演示之后,来详细的讲解一下方法引用
参考:https://blog.youkuaiyun.com/youanyyou/article/details/78993015
- 函数构造器的引用 Class::new
- 静态方法引用 Class::static_method
- 特定类的任意方法引用 Class::method
- 特定对象的引用 instance:method
实例
往User类添加方法引用方法:
public static User create(Supplier<User> supplier){
return supplier.get();
}
public static void updateUsername(User user){
user.setUsername(user.getUsername() + " updated.");
}
public void updateAge(){
this.setAge(this.getAge() + 10);
}
public void changeAge(User user){
user.setAge(user.getAge() + 10);
}
方法测试
public static void main(String[] args) {
List<User> list = initList();
// 1、构造器方法引用
User newUser = User.create(User::new);
newUser.setAge(1);
newUser.setUsername("new");
System.out.println(newUser);
// 2、类静态方法引用
list.forEach(User::updateUsername);
// 3、类普通方法引用
list.forEach(User::updateAge);
// 4、实例方法引用
User user = new User();
list.forEach(user::changeAge);
list.forEach(System.out::println);
}
private static List<User> initList() {
List<User> list = new ArrayList<>();
list.add(new User("oaby", 23));
list.add(new User("tom", 11));
list.add(new User("john", 16));
list.add(new User("jennis", 26));
list.add(new User("tin", 26));
list.add(new User("army", 26));
list.add(new User("mack", 19));
list.add(new User("jobs", 65));
list.add(new User("jordan", 23));
return list;
}
输出结果
User [username=new, age=1]
User [username=oaby updated., age=43]
User [username=tom updated., age=31]
User [username=john updated., age=36]
User [username=jennis updated., age=46]
User [username=tin updated., age=46]
User [username=army updated., age=46]
User [username=mack updated., age=39]
User [username=jobs updated., age=85]
User [username=jordan updated., age=43]