javaSE基础知识——day20 1.8新增日期API,Lambda表达式的方法构造引用,Stream流,筛选切片,映射,排序

编程入门 行业动态 更新时间:2024-10-08 08:23:15

javaSE基础知识——day20 1.8新增日期API,Lambda<a href=https://www.elefans.com/category/jswz/34/1771310.html style=表达式的方法构造引用,Stream流,筛选切片,映射,排序"/>

javaSE基础知识——day20 1.8新增日期API,Lambda表达式的方法构造引用,Stream流,筛选切片,映射,排序

JDK1.8 新增的日期时间API

? LocalDate、 LocalTime、 LocalDateTime类的实例是不可变的对象,
? 分别表示使用 ISO-8601日历系统的日期、时间、日期和时间。
? 它们提供了简单的日期或时间,并不包含当前的时间信息。也不包含与时区相关的信息。
? 注: ISO-8601日历系统是国际标准化组织制定的现代公民的日期和时间的表示法
? 这些新增的日期时间API都在 java.time包下

获取方法
  • 方式1通过静态方法 now();
    例如:LocalDateTime ldt = LocalDateTime.now();

  • 方式2通过静态方法of()方法参数可以指定年月日时分秒
    例如:LocalDateTime of = LocalDateTime.of(2018, 12, 30, 20, 20, 20);

  • 常用方法
    1.获取相关的get系类的方法:
    lad.getYear()获得年
    lad.getMinute()获得分钟
    lad.getHour();获得时间
    getDayOfMonth获得月中天数(1-31)
    getDayOfYear获得年中的天数(1-360)
    getDayOfWeak获得星期几(返回一个 DayOfWeek枚举值)
    getMonth获得月份, 返回一个 Month 枚举值
    getMonthValue获得月份(1-12)
    getYear获得年份

package day20190804.新增的时间日期API;import java.time.*;/*** @description:* @author: @李小白* @create: 2019-08-04 10:09*/
public class Demo01时间日期和get方法 {public static void main(String[] args) {System.out.println("=============now=获得当前日期===============");//now  获得当前日期和时间LocalDate now = LocalDate.now();//获得当前日期LocalTime now1 = LocalTime.now();//获得当前时间LocalDateTime now2 = LocalDateTime.now();//获得当前日期和时间System.out.println(now);System.out.println(now1);System.out.println(now2);System.out.println("============of=可以指定日期==============");//可以指定日期LocalDate of = LocalDate.of(2018, 10, 10);System.out.println(of);LocalDateTime of1 = LocalDateTime.of(2018, 10, 10, 12, 12, 12);System.out.println(of1);System.out.println("===============get方法=============");System.out.println(now2.getYear());System.out.println(now2.getHour());System.out.println(now2.getMinute());System.out.println(now2.getDayOfMonth());System.out.println(now2.getDayOfWeek());System.out.println(now2.getDayOfYear());System.out.println(now2.getMonth());System.out.println(now2.getMonthValue());}
}

2.格式化日期字符串的方法:format()
例如:String yyyy = ldt.format(DateTimeFormatter.ofPattern(“yyyy”));
3.时间日期转换的方法:toLocalDate();toLocalTime();
例如:LocalDate localDate = ldt.toLocalDate();
例如:LocalTime localTime = ldt.toLocalTime();
4.判断的方法
isAfter()判断一个日期是否在指定日期之后
isBefore()判断一个日期是否在指定日期之前
isEqual(); 判断两个日期是否相同
isLeapYear()判断是否是闰年注意是LocalDate类中的方法
例如: boolean after = ldt.isAfter(LocalDateTime.of(2024, 1, 1, 2, 3));
例如 boolean b= LocalDate.now().isLeapYear();

package day20190804.新增的时间日期API;import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;/*** @description:* @author: @李小白* @create: 2019-08-04 10:37*/
public class Demo02格式化日期转换判断日期 {public static void main(String[] args) {LocalDateTime now = LocalDateTime.now();LocalDate now1 = LocalDate.now();LocalTime now2 = LocalTime.now();LocalDateTime of = LocalDateTime.of(2018,11,4,11,11,11);System.out.println("===============格式化日期==============");//自己指定日期格式String format = now.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"));System.out.println(format);System.out.println("=================时间日期转换的方法===================");LocalDate localDate = now.toLocalDate();LocalTime localTime = now.toLocalTime();System.out.println("==================判断日期=====================");//两个日期对比前后System.out.println(now.isAfter(of));//是否在之前System.out.println(now.isBefore(of));//是否在之后System.out.println(now.isEqual(of));//是否相等System.out.println(now1.isLeapYear());//是否是瑞年}
}

5.解析的静态方法:parse(“2007-12-03T10:15:30”);
paser() 将一个日期字符串解析成日期对象,注意字符串日期的写法的格式要正确,否则解析失败

例如:LocalDateTime parse = LocalDateTime.parse(“2007-12-03T10:15:30”);

按照我们指定的格式去解析,格式要对应,否则报错
LocalDateTime ldt4 = LocalDateTime.now();
DateTimeFormatter formatter2 = DateTimeFormatter.ofPattern(“yyyy-MM-dd HH:mm:ss”);
LocalDateTime.parse(“2018-01-21 20:30:36”, formatter2);

package day20190804.新增的时间日期API;import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;/*** @description:* @author: @李小白* @create: 2019-08-04 10:57*/
public class Demo03解析日期 {public static void main(String[] args) {//        String str="yyyy-MM-ddTHH:mm:ss";System.out.println("-------按照默认的形式解析------");LocalDateTime parse = LocalDateTime.parse("2007-12-03T10:15:30");System.out.println(parse);System.out.println("-----按照我们指定的格式进行解析------");DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH时mm分ss秒");LocalDateTime parse1 = LocalDateTime.parse("2007年12月05日 10时15分30秒", dateTimeFormatter);System.out.println(parse1);}
}

6.添加年月日,时分秒方法pluse 系列,会返回一新的对象
LocalDateTime localDateTime = ldt.plusYears(1);
LocalDateTime localDateTime1 = ldt.plusMonths(3);
LocalDateTime localDateTime2=ldt.plusHours(10);
7.减去年月日,时分秒的方法minus系列方法,会返回一个新的对象
例如:LocalDateTime localDateTime2 = ldt.minusYears(8);
8.指定年月日时分秒的方法 with系列的方法,都会返回一个新的对象
例如 LocalDateTime localDateTime3 = ldt.withYear(1998);
//获取这个月的第几个星期几是几号,比如 TemporalAdjusters.dayOfWeekInMonth(2, DayOfWeek.FRIDAY) 代表的意思是这个月的第二个星期五是几号
// TemporalAdjusters.dayOfWeekInMonth(2, DayOfWeek.FRIDAY)
LocalDateTime with1 = now.with(TemporalAdjusters.dayOfWeekInMonth(2,DayOfWeek.FRIDAY));

package day20190804.新增的时间日期API;import java.time.DayOfWeek;
import java.time.LocalDateTime;
import java.time.temporal.TemporalAdjusters;/*** @description: 添加和减去年月日* @author: @李小白* @create: 2019-08-04 11:18*/
public class Demo04添加年月日pluse减去with {public static void main(String[] args) {LocalDateTime now = LocalDateTime.now();System.out.println("==============添加pluse系列=========");System.out.println(now.plusDays(2));//在现在的基础上+2天System.out.println(now.plusMonths(3));//在现在的基础上+3个月System.out.println(now.plusYears(5));//在现在的基础上+5年System.out.println("==========减少with系列============");//指定日期System.out.println(now.withHour(3));//减少到3点System.out.println(now.withYear(2005));//减少到2005年System.out.println(now.withDayOfMonth(2));//指定日期,第一天,最后一天System.out.println(now.with(TemporalAdjusters.firstDayOfMonth()));//这个月的第一天System.out.println(now.with(TemporalAdjusters.firstDayOfNextMonth()));//下个月的第一天System.out.println(now.with(TemporalAdjusters.next(DayOfWeek.FRIDAY)));//指定下周五System.out.println(now.with(TemporalAdjusters.next(DayOfWeek.SUNDAY)));//指定下周日System.out.println(now.with(TemporalAdjusters.next(DayOfWeek.SATURDAY)));//指定下周六}
}

DInstant 时间戳类从1970-01-01 00:00:00 截止到当前时间的毫秒值

1获取对象的方法 now(),默认是美国时间和我们相差8小时
Instant ins = Instant.now();
2.在Instant中设置偏移量的方法:atOffset() 设置偏移量
OffsetDateTime time = ins.atOffset(ZoneOffset.ofHours(8));
System.out.println(time);

3.获取系统本地默认时区时间的方法atZone()
ZonedDateTime zonedDateTime = ins.atZone(ZoneId.systemDefault());
System.out.println(zonedDateTime);

4.get系列的方法
getEpochSecond() 获取从1970-01-01 00:00:00到当前时间的秒值
toEpochMilli();获取从1970-01-01 00:00:00到当前时间的毫秒值
getNano()方法是把获取到的当前时间的秒数 换算成纳秒
long epochSecond = ins.getEpochSecond();//获取从1970-01-01 00:00:00到当前时间的秒值
getNano()方法是把获取到的当前时间的豪秒数 换算成纳秒 比如当前时间是2018-01-01 14:00:20:30
那就把30豪秒换算成纳秒 int nano = ins.getNano();

  1. ofEpochSecond()方法 给计算机元年增加秒数
    ofEpochMilli() 给计算机元年增加毫秒数
    例如 Instant instant = Instant.ofEpochSecond(5);
    System.out.println(instant);
    单位换算
    0.1 毫秒 = 10 的5次方纳秒 = 100000 纳秒
    1 毫秒 = 1000 微妙 = 1000000 纳秒
package day20190804.新增的时间日期API;import java.time.Instant;
import java.time.ZoneId;
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.util.Set;/*** @description: DInstant时间戳类,当前时间,偏移量时区,时间设置,get方法* @author: @李小白* @create: 2019-08-04 11:40*/
public class Demo05Instant时间戳类当前偏移量get {public static void main(String[] args) {Instant ins = Instant.now();System.out.println(ins);//输出来的时间是美国时间System.out.println("===============获取自己的时区==============");System.out.println(ins.atOffset(ZoneOffset.ofHours(8)));//设置我们自己的东八区System.out.println(ins.atZone(ZoneId.systemDefault()));//获取系统默认的时区System.out.println("--------通过检索亚洲获取时区-------");Set<String> availableZoneIds = ZoneId.getAvailableZoneIds();for (String availableZoneId : availableZoneIds) {if(availableZoneId.startsWith("Asia")){System.out.println(availableZoneId);}}System.out.println("=========get方法=to=of============");System.out.println(ins.getEpochSecond());//获取当前时间的的秒值System.out.println(ins.toEpochMilli());//获取当前时间的毫秒值System.out.println(Instant.ofEpochSecond(60 * 60));//给计算机元年增加秒数System.out.println(Instant.ofEpochMilli(1000 * 60 * 06));//给计算机原年增加毫秒数}
}

Duration : 用于计算两个“时间”间隔的类

Period : 用于计算两个“日期”间隔的类

Duration类中静态方法between()
Instant start = Instant.now();
for(int i=0;i<1000L;i++){
System.out.println(“循环内容”);
}
Instant end = Instant.now();
静态方法:between() 计算两个时间的间隔,默认是秒
Duration between = Durati’on.between(start, end);
Duration中的toMillis()方法:将秒转成毫秒
System.out.println(between.toMillis());

Period类 中的静态方法between()
计算两个日期之间的间隔
LocalDate s = LocalDate.of(1985, 03, 05);
LocalDate now = LocalDate.now();
Period be = Period.between(s, now);
System.out.println(be.getYears());间隔了多少年
System.out.println(be.getMonths());间隔了多少月
System.out.println(be.getDays());间隔多少天

package day20190804.新增的时间日期API;import java.time.Duration;
import java.time.Instant;
import java.time.LocalDate;
import java.time.Period;/*** @description:duration period* @author: @李小白* @create: 2019-08-04 12:01*/
public class Demo06计算时间间隔日期间隔 {public static void main(String[] args) {System.out.println("=============计算时间间隔=duration==========");Instant str = Instant.now();for (int i = 0; i < 10000; i++) {System.out.println(' ');}Instant end = Instant.now();Duration duration = Duration.between(str, end);System.out.println(duration.toMillis());//将时间间隔转成毫秒值输出System.out.println("==========计算日期间隔=preiod===========");LocalDate now = LocalDate.now();LocalDate of = LocalDate.of(2016,11,4);Period between = Period.between(of, now);System.out.println(between.getYears());System.out.println(between.getMonths());System.out.println(between.getDays());}
}

TemporalAdjuster : 时间校正器,是个接口

例如:
LocalDate now = LocalDate.now();
System.out.println(now);
1 使用TemporalAdjusters自带的常量来设置日期
LocalDate with = now.with(TemporalAdjusters.lastDayOfYear());
System.out.println(with);
2 采用TemporalAdjusters中的next方法来指定日期
LocalDate date = now.with(TemporalAdjusters.next(DayOfWeek.SUNDAY));
System.out.println(date);
例如:TemporalAdjusters.next(DayOfWeek.SUNDAY) 本周的星期天
例如:TemporalAdjusters.nextOrSame(DayOfWeek.MONDAY) 下一周的星期一
3 采用自定义的方式来指定日期 比如指定下个工作日
LocalDateTime ldt = LocalDateTime.now();
LocalDateTime workDay = ldt.with(new TemporalAdjuster() {
@Override
public Temporal adjustInto(Temporal temporal) {
//向下转型
LocalDateTime ld = (LocalDateTime) temporal;
//获取这周的星期几
DayOfWeek dayOfWeek = ld.getDayOfWeek();
if (dayOfWeek.equals(DayOfWeek.FRIDAY)) {
return ld.plusDays(3);//如果这天是星期五,那下个工做日就加3天
} else if (dayOfWeek.equals(DayOfWeek.SATURDAY)) {
return ld.plusDays(2);//如果这天是星期六,那下个工做日就加2天
} else {
//其他就加一天
return ld.plusDays(1);
}
}
});

System.out.println(workDay);
package day20190804.新增的时间日期API;import java.time.DayOfWeek;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.temporal.Temporal;
import java.time.temporal.TemporalAdjuster;
import java.time.temporal.TemporalAdjusters;/*** @description: 指定日期,可以自定义指定日期* @author: @李小白* @create: 2019-08-04 13:38*/
public class Demo07TemporalAdjusters {public static void main(String[] args) {LocalDateTime now = LocalDateTime.now();LocalDateTime with = now.with(TemporalAdjusters.firstDayOfNextMonth());//下个月的第一天System.out.println(with);LocalDateTime with1 = now.with(TemporalAdjusters.next(DayOfWeek.SUNDAY));//本周的周一,如果时间过去了,就会自定调节成下周的周一System.out.println(with1);LocalDateTime with2 = now.with(TemporalAdjusters.nextOrSame(DayOfWeek.MONDAY));System.out.println(with2);//下周的周一System.out.println("===========采用自定义的方式指定日期=========");// 3 采用自定义的方式来指定日期 比如指定下个工作日//今天如果时星期五 下个工作日 +3//今天如果时星期六 下个工作日 +2//其他 +1LocalDateTime newDate = now.with(new TemporalAdjuster() {@Overridepublic Temporal adjustInto(Temporal temporal) {// temporal 当前日期//向下转型LocalDate localDate= (LocalDate) temporal;//后期当前日期时星期几DayOfWeek dayOfWeek = localDate.getDayOfWeek();if(dayOfWeek.equals(DayOfWeek.FRIDAY)){LocalDate localDate1 = localDate.plusDays(3);return localDate1;}else if(dayOfWeek.equals(DayOfWeek.SATURDAY)){LocalDate localDate1 = localDate.plusDays(2);return localDate1;}else{LocalDate localDate1 = localDate.plusDays(1);return localDate1;}}});System.out.println(newDate);}
}

DateTimeFormatter :解析和格式化日期或时间的类

方法有5种

方法一

1.获取对象的方式,通过静态方法ofPattern(“yyyy-MM-dd”)
DateTimeFormatter dateFormat = DateTimeFormatter.ofPattern(“yyyy-MM-dd”);
LocalDateTime now = LocalDateTime.now();
2.format()方法把一个日期对象的默认格式 格式化成指定的格式
String format1 = dateFormat.format(now);
System.out.println(format1);
3.格式化日期 方式2使用日期类中的format方法 传入一个日期格式化类对象

LocalDateTime now1 = LocalDateTime.now();
使用日期类中的format方法 传入一个日期格式化类对象
使用DateTimeFormatter中提供好的日期格式常量
now1.format(DateTimeFormatter.ISO_LOCAL_DATE_TIME);

4.使用自定义的日期格式格式化字符串
DateTimeFormatter timeFormat = DateTimeFormatter.ofPattern(“yyyy-MM-dd HH:mm:ss”);//自定义一个日期格式
String time = now1.format(timeFormat);
System.out.println(time);

  1. 把一个日期字符串转成日期对象使用日期类中的parse方法传入一个日期字符串,传入对应的日期格式化类
    DateTimeFormatter dateFormat = DateTimeFormatter.ofPattern(“yyyy-MM-dd”);
    LocalDateTime parse = LocalDateTime.parse(time, timeFormat);
    System.out.println(parse);
package day20190804.新增的时间日期API;import java.time.LocalDate;
import java.time.format.DateTimeFormatter;import static java.time.format.DateTimeFormatter.*;/*** @description:* @author: @李小白* @create: 2019-08-04 13:52*/
public class Demo08DataTimeFormat的5种方法 {public static void main(String[] args) {DateTimeFormatter dateTimeFormatter = ofPattern("yyyy年MM月dd");System.out.println("===============方式一=============");//方式1 可以使用DateTimeFormatter 他的format()LocalDate now = LocalDate.now();String format = dateTimeFormatter.format(now);System.out.println(format);System.out.println("============方式二===============");//方式2  使用 LocalDate 的format方法String format1 = now.format(dateTimeFormatter);System.out.println(format1);System.out.println();System.out.println("============方式三============");//使用自带的格式String format2 = now.format(DateTimeFormatter.ISO_DATE);System.out.println(format2);//把字符串解析成日期String str="2019-09-04";LocalDate parse = LocalDate.parse(str);System.out.println(parse);String str2="2019年11月11日";DateTimeFormatter dateTimeFormatter1 = DateTimeFormatter.ofPattern("yyyy年MM月dd日");LocalDate parse1 = LocalDate.parse(str2, dateTimeFormatter1);System.out.println(parse1);}
}

ZonedDate,ZonedTime、ZonedDateTime : 带时区的时间或日期

? 用法和 LocalDate、 LocalTime、 LocalDateTime 一样 只不过ZonedDate,ZonedTime、ZonedDateTime 这三个带有当前系统的默认时区

ZoneID 世界时区类

1.获取世界各个地方的时区的集合 的方法getAvailableZoneIds()
? 使用ZoneID中的静态方法getAvailableZoneIds();来获取
? 例如:Set availableZoneIds = ZoneId.getAvailableZoneIds();
? 2.获取系统默认时区的ID
? ZoneId zoneId = ZoneId.systemDefault(); //Asia/Shanghai
? 3.获取带有时区的日期时间对象
? //创建日期对象
? LocalDateTime now = LocalDateTime.now();
? //获取不同国家的日期时间根据各个地区的时区ID名创建对象
? ZoneId timeID = ZoneId.of(“Asia/Shanghai”);
? //根据时区ID获取带有时区的日期时间对象
? ZonedDateTime time = now.atZone(timeID);
? System.out.println(time);
? //方式2 通过时区ID 获取日期对象

package day20190804.新增的时间日期API;import java.time.ZoneId;
import java.time.ZonedDateTime;
import java.util.Set;/*** @description: 获取世界各个地方的时间ID、* @author: @李小白* @create: 2019-08-04 14:12*/
public class Demo09获取时间ID {public static void main(String[] args) {//##ZonedDate, ZonedTime、ZonedDateTime :带时区的时间或日期////        ? 用法和 LocalDate、LocalTime、LocalDateTime 一样 只不过ZonedDate, ZonedTime、ZonedDateTime 这三个带有当前系统的默认时区//LocalDateTimeZonedDateTime now = ZonedDateTime.now();System.out.println(now);// ZoneID 世界时区类ZoneId zoneId = ZoneId.systemDefault();System.out.println(zoneId);Set<String> availableZoneIds = ZoneId.getAvailableZoneIds();}
}

JDK1.8的新特性之Lambda表达式的学习

概念:Lambda 是一个匿名函数,我们可以把 Lambda表达式理解为是一段可以传递的代码(将代码像数据一样进行传递)。可以写出更简洁、更灵活的代码。

package day20190804.lambda表达式;import java.util.Arrays;
import java.util.Comparator;
import java.util.List;/*** @description: lambda* @author: @李小白* @create: 2019-08-04 14:55*/
public class Demo01第一个lambda表达式 {public static void main(String[] args) {//JDK1.8 引入一种语法 Lambda 表达式 ,你 可以理解为是匿名内部类的一种简写方式,但是有条件// Lambda表达式要用到 -> 箭头符号// 以 -> 箭头符号 分为左右两半// 箭头左边是重写接口中抽象方法的参数列表 ()->// 箭头右边是对接口中抽象方法的重写逻辑 ->重写逻辑List<Integer> list = Arrays.asList(10, 23, 45, 67, 89);//匿名内部类的写法list.sort(new Comparator<Integer>() {@Overridepublic int compare(Integer a, Integer b) {return a-b;}});//简写的lambda表达式//第一步 简写list.sort((Integer x,Integer y)->{return x-y;});//第二步 简写list.sort((x,y)->{return  x-y;});//第三步简写:如果你对方法实现逻辑只有一行,可以省略{} 和  return//但是如果,你对接口中的抽象方法的实现逻辑不是一行,就不能省略{}和return//第三步  简写list.sort((x,y)->x-y);}
}

什么是函数式接口

函数式接口的定义是: 只包含一个抽象方法的接口

  • Java中提供的4大核心函数式接口
    函数式接口 参数类型 返回类型 用途
    1.Consumer
    消费型接口 T void 对类型为T的对象应用操作,包含方法:void accept(T t)
    2.Supplier
    供给型接口 无 T 返回类型为T的对象,包含方法: T get();
    3.Function<T, R>
    函数型接口T R 对类型为T的对象应用操作,并返回结果。结果是R类型的对象。包含方法: R apply(T t);
    4.Predicate
    断言型接口T boolean 确定类型为T的对象是否满足某约束,并返回boolean 值。包含方法boolean test(T t);
package day20190804.lambda表达式;/*** @description: 函数式接口* @author: @李小白* @create: 2019-08-04 15:04*/
public class Demo02函数式接口 {public static void main(String[] args) {Demo02show方法 demo02 = new Demo02show方法() {@Overridepublic void show() {System.out.println(100);}};//lamble表达式//使用Lambda表达式简写Demo02show方法 demos02 = ()-> System.out.println(100);//使用可变参数进行写lambda表达式myTest(()->System.out.println(100));}private static void myTest(Demo02show方法 my) {my.show();}
}
package day20190804.lambda表达式;/*** @description:* @author: @李小白* @create: 2019-08-04 15:05*/
public interface Demo02show方法 {void show();
}
package day20190804.lambda表达式;import java.util.function.Consumer;
import java.util.function.Supplier;/*** @description: 函数式接口* @author: @李小白* @create: 2019-08-04 15:17*/
public class Demo03java给我们提供的函数式接口 {public static void main(String[] args) {//Java 给我们提供了一些函数式接口Consumer<Integer> con= integer -> System.out.println(integer);// Consumer<Integer> con2=b-> System.out.println(b);Supplier<String> supplier = () -> "abc";}
}

方法引用与构造器引用

  • 方法引用?
    方法引用其实是Lambda表达式的另一种写法,当要传递给Lambda体的操作,已经有实现的方法了,可以使用方法引用.
  • 注意:
    实现抽象方法的参数列表,必须与方法引用方法的参数列表保持一致!
  • 方法引用
    使用操作符 “ ::” 将方法名和对象或类的名字分隔开来。
  • 如下三种主要使用情况:
    对象::实例方法
    类::静态方法
    类::实例方法
package day20190804.lambda表达式;import java.util.function.BiFunction;
import java.util.function.Consumer;
import java.util.function.Function;/*** @description: 方法引用* @author: @李小白* @create: 2019-08-04 15:40*/
public class Demo04方法引用 {public static void main(String[] args) {Consumer<String> consumer = new Consumer<String>() {@Overridepublic void accept(String s) {System.out.println(s);}};consumer.accept("哈哈");Consumer<String> consumer2= x-> System.out.println(x);consumer2.accept("呵呵");//再次对Lambda表达式简写//这种简写叫做方法引用//你对接口中的抽象方法的实现逻辑中调用的这个方法,跟接口中的这个方法的返回值和形参列表一致的化,就可以用方法引用再次简写Consumer<String> consumer3=System.out::println;consumer3.accept("哈哈哈哈哈");System.out.println("--------------------------------");Function<String, Integer> function = new Function<String, Integer>() {@Overridepublic Integer apply(String s) {//一个参数,一个返回值int i = Integer.parseInt(s);//一个参数,一个返回值return i;}};Function<String, Integer> function2 =(x)->Integer.parseInt(x);Function<String, Integer> function3=Integer::parseInt;System.out.println("-------------------------");BiFunction<Double, Double, Double> biFunction = new BiFunction<Double, Double, Double>() {@Overridepublic Double apply(Double aDouble, Double aDouble2) {Math.max(aDouble, aDouble2);return null;}};BiFunction<Double, Double, Double> biFunction2=(a,b)->Math.max(a,b);//方法引用BiFunction<Double, Double, Double> biFunction3=Math::max;System.out.println("--------------------------");Function<Integer, String> function1 = new Function<Integer, String>() {@Overridepublic String apply(Integer s) {String s1 = String.valueOf(s);return s1;}};Function<Integer, String> function4=String::valueOf;}
}

构造器引用


public class MyTest {public static void main(String[] args) {//JDK1.8时间日期API// LocalDate//  LocalDateTime//  LocalTime// DateTimeFormatter// Instant// Duration// Period// ZoneId// Lambda     接口中抽象方法的参数列表->你对抽象方法的实现逻辑//函数式接口,才支持Lambda   @FunctionalInterface 注解 是一个函数式样接口// 方法引用:你再重写接口中的方法时,不经意间,调用了一个方法,这个方法的形参和返回值,正好能跟这个抽象方法的形参和返回值,对应上,就可以使用方法引用简写//构造引用Supplier<MyClass> supplier = new Supplier<MyClass>() {@Overridepublic MyClass get() {return new MyClass();}};Supplier<MyClass> supplier2 = () -> new MyClass();//构造引用Supplier<MyClass> supplier3 = MyClass::new;Function<String, MyClass> function = new Function<String, MyClass>() {@Overridepublic MyClass apply(String s) {return new MyClass(s);}};MyClass zhangsan = function.apply("zhangsan");Function<String, MyClass> function2 =(s)->new MyClass(s);Function<String, MyClass> function3 =MyClass::new;}
}

Stream API(java.util.stream.*)

  • 概念:Stream API 提供了一种高效且易于使用的处理数据的方式。
    Stream 是 Java8 中处理集合的关键抽象概念,它可以指定你希望对集合进行的操作,可以执行非常复杂的查找、过滤和映射数据等操作。
    使用Stream API 对集合数据进行操作,就类似于使用 SQL 执行的数据库查询。也可以使用 Stream API 来并行执行操作。
流(Stream) 到底是什么呢?

是数据渠道,用于操作数据源(集合、数组等)所生成的元素序列

集合讲的是数据,流讲的是计算!

注意:

1.Stream流不会存储元素
2.Stream流不会改变原对象,他们会返回一个新的流
3.Stream流是演示操作,到需要结果的时候才执行

Steam流操作的三个步骤

1.创建一个Stream数据源
2.中间操作:对数据源的数据进行处理
3终止操作:执行中间操作链并产生结果

创建Stream流的4种方式

1.Java8 中的 Collection 接口被扩展,提供了
两个获取流的方法:
 default Stream stream() : 返回一个顺序流
 default Stream parallelStream() : 返回一个并行流
2.Java8 中的 Arrays 的静态方法 stream() 可以获取数组流:
 static Stream stream(T[] array): 返回一个流
重载形式,能够处理对应基本类型的数组:
public static IntStream stream(int[] array)
 public static LongStream stream(long[] array)
 public static DoubleStream stream(double[] array)
3.由值创建流,可以使用静态方法 Stream.of(), 通过显示值创建一个流。它可以接收任意数量的参数。
 public static Stream of(T… values) : 返回一个流
4.由函数创建流:创建无限流可以使用静态方法 Stream.iterate()和Stream.generate(), 创建无限流。
public static Stream iterate(final T seed, finalUnaryOperator f) 迭代
public static Stream generate(Supplier s) 生成

package day20190804.Stream流;import java.util.Arrays;
import java.util.List;
import java.util.function.UnaryOperator;
import java.util.stream.Stream;/*** @description:创建Stream流的5中方式* @author: @李小白* @create: 2019-08-04 16:04*/
public class Demo01的5个方式 {public static void main(String[] args) {//方式一  集合中的一个方法StreamList<Integer> list = Arrays.asList(12, 34, 56, 78, 89);Stream<Integer> stream = list.stream();//方式二: Arrays中的一个静态方法Stream<Integer> stream1 = Arrays.stream(new Integer[]{12, 34, 35, 67, 98});//方式三:Stream中的静态方法ofStream<Integer> integerStream = Stream.of(32, 34, 67, 34, 65, 87);//方式四:创建一个无限久流Stream<Integer> iterate = Stream.iterate(1, new UnaryOperator<Integer>() {@Overridepublic Integer apply(Integer integer) {return integer + 1;}});//中间操作执行完了之后,返回一个持有结果的新流Stream<Integer> limit = iterate.limit(9);//只要其中的9个//没有进行终止操作中间环节不执行,主要体现的是一种延迟的思想limit.forEach(System.out::println);//创建出一个无限流Stream.generate(()->Math.random()).limit(5).forEach(System.out::println);}
}

Stream流的中间操作

多个中间操作可以连成一个流水线,中间操作不触发终止操作,则不会执行任何的处理

在终止行擦操作一次性处理的现象,被称为:“惰性求值”

1.筛选与切片filter()distinct()

	filter(Predicate p) 过滤 接收 Lambda , 从流中排除某些元素。distinct() 去重,通过流所生成元素的 hashCode() 和 equals() 去除重复元素limit(long maxSize) 截断流,使其元素不超过给定数量。skip(long n)	    跳过元素,返回一个扔掉了前 n 个元素的流。若流中元素不足 n 个,则返回一个空流。与 limit(n) 互补
package day20190804.Stream流;public class Employee {private int id; //员工的idprivate String name; //员工的姓名private int age; //员工的年龄private double salary; //员工的工资private Status status; //员工的状态public Employee() {}public Employee(String name) {this.name = name;}public Employee(String name, int age) {this.name = name;this.age = age;}public Employee(int id, String name, int age, double salary) {this.id = id;this.name = name;this.age = age;this.salary = salary;}public Employee(int id, String name, int age, double salary, Status status) {this.id = id;this.name = name;this.age = age;this.salary = salary;this.status = status;}public Status getStatus() {return status;}public void setStatus(Status status) {this.status = status;}public int getId() {return id;}public void setId(int id) {this.id = id;}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 double getSalary() {return salary;}public void setSalary(double salary) {this.salary = salary;}public String show() {return "测试方法引用!";}@Overridepublic int hashCode() {final int prime = 31;int result = 1;result = prime * result + age;result = prime * result + id;result = prime * result + ((name == null) ? 0 : name.hashCode());long temp;temp = Double.doubleToLongBits(salary);result = prime * result + (int) (temp ^ (temp >>> 32));return result;}@Overridepublic boolean equals(Object obj) {if (this == obj)return true;if (obj == null)return false;if (getClass() != obj.getClass())return false;Employee other = (Employee) obj;if (age != other.age)return false;if (id != other.id)return false;if (name == null) {if (other.name != null)return false;} else if (!name.equals(other.name))return false;if (Double.doubleToLongBits(salary) != Double.doubleToLongBits(other.salary))return false;return true;}@Overridepublic String toString() {return "Employee [id=" + id + ", name=" + name + ", age=" + age + ", salary=" + salary + ", status=" + status+ "]";}//枚举public enum Status {FREE, //空闲BUSY, //繁忙VOCATION;//休假}}
package day20190804.Stream流;import java.util.Arrays;
import java.util.List;
import java.util.stream.Stream;/*** @description: 筛选与切片* @author: @李小白* @create: 2019-08-04 16:25*/
public class Demo02筛选与切片 {public static  void main(String[] args) {//1. 筛选与切片//filter(Predicate p) 过滤 接收 Lambda ,从流中排除某些元素。//distinct() 去重,通过流所生成元素的 hashCode () 和 equals () 去除重复元素//limit( long maxSize)截断流,使其元素不超过给定数量。//skip( long n)跳过元素,返回一个扔掉了前 n 个元素的流。若流中元素不足 n 个,则返回一个空流。与 limit (n) 互补//        1. 创建 Stream
//        一个数据源(如:集合、数组),获取一个流
//2. 中间操作
//        一个中间操作链,对数据源的数据进行处理
//3. 终止操作(终端操作)
//        一个终止操作,执行中间操作链,并产生结果List<Employee>  emps= Arrays.asList(new Employee(102, "李四", 59, 6666.66),new Employee(101, "张三", 18, 9999.99),new Employee(103, "王五", 28, 3333.33),new Employee(104, "赵六", 8, 7777.77),new Employee(104, "赵六", 8, 7777.77),new Employee(104, "赵六", 8, 7777.77),new Employee(105, "田七", 38, 5555.55));System.out.println("================获取工作大于8000的员工==============");//获取流Stream<Employee> stream = emps.stream();//中间操作Stream<Employee> employeeStream = stream.filter(e -> e.getSalary() > 8000);System.out.println(employeeStream);//终止操作employeeStream.forEach(System.out::println);System.out.println("==========获取姓赵的员工===============");//获得流Stream<Employee> stream1 = emps.stream();//中间操作Stream<Employee>  name= stream1.filter(e -> e.getName().startsWith("赵"));System.out.println(name);//终止操作name.forEach(System.out::println);System.out.println("=========从头开始截取几个元素============");List<Integer> list = Arrays.asList(12, 34, 56, 67, 89, 90, 9);Stream<Integer> limit = list.stream().limit(4);System.out.println(limit);System.out.println("=========从头开始跳过几个元素============");List<Integer> list2 = Arrays.asList(12, 34, 56, 67, 89, 90, 9);Stream<Integer> skip = list2.stream().skip(3);System.out.println(skip);}
}

2.映射

	map(Function f)			接收一个函数作为参数,该函数会被应用到每个元素上,并将其映射成一个新的元素。flatMap(Function f)		接收一个函数作为参数,将流中的每个值都换成另一个流,然后把所有流连接成一个流.mapToDouble(ToDoubleFunction f)	接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 DoubleStream。mapToInt(ToIntFunction f)	接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 IntStream。mapToLong(ToLongFunction f)	接收一个函数作为参数,该函数会被应用到每个元素上,产生一个新的 LongStream。

案例一:把名字取出来

package day20190804.Stream流;import java.util.Arrays;
import java.util.List;
import java.util.function.Function;
import java.util.stream.Stream;/*** @description:* @author: @李小白* @create: 2019-08-04 16:58*/
public class Demo03映射 {public static void main(String[] args) {//2. 映射//map(Function f) 接收一个函数作为参数,该函数会被应用到每个元素上,并将其映射成一个新的元素。//flatMap(Function f) 接收一个函数作为参数,将流中的每个值都换成另一个流,然后把所有流连接成一个流.//List<Employee> emps = Arrays.asList(new Employee(102, "李四", 59, 6666.66),new Employee(101, "张三", 18, 9999.99),new Employee(103, "王五", 28, 3333.33),new Employee(104, "赵六", 8, 7777.77),new Employee(104, "赵六", 8, 7777.77),new Employee(104, "赵六", 8, 7777.77),new Employee(105, "田七", 38, 5555.55));System.out.println("=============把名字取出来==============");//获取流Stream<Employee> stream = emps.stream();//中间操作Stream<String> stringStream = stream.map(e -> e.getName());System.out.println(stringStream);//终止操作stringStream.forEach(System.out::println);System.out.println("=====把集合中的小写元素变成大写======");List<String> strings = Arrays.asList("aaa", "bbb", "ccc");Stream<String> stream1 = strings.stream();stream1.map(new Function<String, String>() {@Overridepublic String apply(String s) {String s1 = s.toUpperCase();return s1;}}).forEach(System.out::println);}
}

案例二:把字符串截取成单独的字符

package day20190804.Stream流;import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.stream.Stream;/*** @description: 把字符串截成字符放到流中* @author: @李小白* @create: 2019-08-04 17:11*/
public class Demo04把字符串截成字放到流中 {public static void main(String[] args) {List<String> list = Arrays.asList("aaa", "bbb", "ccc");Stream<String> stream = list.stream();//中间操作Stream<Stream<Character>> streamStream = stream.map(new Function<String, Stream<Character>>() {@Overridepublic Stream<Character> apply(String s) {Stream<Character> aChar = getChar(s);//抽出一个方法出来return null;}});//终止操作streamStream.forEach(new Consumer<Stream<Character>>() {@Overridepublic void accept(Stream<Character> characterStream) {characterStream.forEach(System.out::println);}});}private static Stream<Character> getChar(String str) {ArrayList<Character> characters = new ArrayList<>();for (char ch : str.toCharArray()) {characters.add(ch);}return characters.stream();}
}

案例三:算阶乘

List<Integer> integers = Arrays.asList(10, 20, 30, 40);Stream<Integer> stream = integers.stream();Stream<Double> doubleStream = stream.map(new Function<Integer, Double>() {@Overridepublic Double apply(Integer integer) {return Math.pow(integer, 2);}});doubleStream.forEach(System.out::println);}

3.排序

	sorted()	产生一个新流,其中按自然顺序排序   元素实现Compareble接口sorted(Comparator comp)	产生一个新流,其中按比较器顺序排序  传入一个比较

**Stream 的终止操作
终端操作会从流的流水线生成结果。其结果可以是任何不是流的值,例如:List、Integer,甚至是 void 。

更多推荐

javaSE基础知识——day20 1.8新增日期API,Lambda表达式的方法构造引用,Stream流,筛选切片,映射,排序

本文发布于:2024-02-27 19:15:30,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1766201.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:表达式   切片   基础知识   日期   方法

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!