JDK 8十大新特性

14299 ワード

前編<<次編>>Java集合クラス図総覧
1.Lambda式
Lambda左(パラメータ)->右(本体コンテンツ)の利点:コードが簡単で、将来のプログラミングトレンドを表す可能性があります.欠点:デバッグが容易ではありません.他のプログラマーがlambda式を学んだことがなければ、コードは他の言語のプログラマーに理解されにくいです.
new Thread(()->{System.out.println(Thread.currentThread().getName()+"    ");}).start();
list.forEach(System.out::println);

2.Stream関数式アクションフロー要素の集合
ストリームAPIを使用してコレクションデータを操作すると、sqlを使用して実行されるデータベースクエリーと同様です.ストリームAPIを使用して、動作を並列に実行することもできます.
  • (1)ストリームを作成する方法
  • /**       ,   Stream.of Arrays.stream    */
    Integer[] integers = {1,2,3,4};
    Stream integers1 = Stream.of(integers);
    integers1.forEach(System.out::println);
    System.out.println("---------------------");
    Stream stream = Arrays.stream(integers);
    stream.forEach(System.out::println);
    System.out.println("---------------------");
    
    /**     Collection   ,         stream  , :Set,List,SortedSet   */
    List list = new ArrayList<>();
    list.add(1);
    list.add(2);
    list.add(3);
    list.add(4);
    stream = list.stream();
    stream.forEach(System.out::println);
    System.out.println("---------------------");
    
    Map map = new HashMap();
    map.put("1","1");
    map.put("2","2");
    map.put("3","3");
    map.put("4","4");
    Set set = map.entrySet();
    Stream stream1 = set.stream();
    stream1.forEach(System.out::println);
    System.out.println("---------------------");
    /** Stream   generate  ,     --  limit       */
    Stream generate = Stream.generate(() -> Math.random());
    generate.limit(10).forEach(d -> System.out.println(d));
    
  • (2)中間操作
  •  List userList = new ArrayList<>();
     userList.add(new User("  ",18));
     userList.add(new User("  ",19));
     userList.add(new User("  ",18));
     userList.add(new User("   ",20));
     userList.add(new User("  ",18));
     /**       */
     //filter-      18    
    userList.stream().filter(user -> user.getAge() > 18).forEach(System.out::println);
     System.out.println("---------------------");
     //limit-               
     userList.stream().sorted(((o1, o2) -> o2.getAge()-o1.getAge())).limit(2).forEach(System.out::println);
     System.out.println("---------------------");
     //skip-    
     userList.stream().skip(2).forEach(System.out::println);
     System.out.println("---------------------");
     //distinct--  --    hashcode equals  
     userList.stream().distinct().forEach(System.out::println);
    
     System.out.println("---------------------");
     /**    */
     //map——               ---  user          list  
     List collect = userList.stream().map(user -> user.getAge()).distinct().collect(Collectors.toList());
     collect.forEach(System.out::println);
     System.out.println("---------------------");
     //flatMap-                ,        
     List> listList = new ArrayList<>();
     listList.add(userList);
     listList.add(userList);
     Stream userStream = listList.stream().flatMap(users -> users.stream());
     userStream.forEach(System.out::println);
    
  • (3)端末動作
  • //anyMatch——          ,            
    boolean flg = userList.stream().anyMatch(user -> user.getName().indexOf(" ") >= 0);
    System.out.println(flg);
    System.out.println("---------------------");
    //max--           
    Optional max = userList.stream().max((o1, o2) -> o1.getAge() - o2.getAge());
    System.out.println(max.get());
    System.out.println("---------------------");
    //  reduce--      
    Optional reduce = userList.stream().map(user -> user.getAge()).reduce((user, user2) -> user + user2);
    System.out.println(reduce.get());
    System.out.println("---------------------");
    //collect()          
    //    18      
    List collect = userList.stream().filter(user -> user.getAge() > 18).collect(Collectors.toList());
    collect.forEach(System.out::println);
    System.out.println("---------------------");
    //          
    Map collect1 = userList.stream().collect(Collectors.groupingBy(user -> user, Collectors.counting()));
    collect1.entrySet().forEach(System.out::println);
    System.out.println("---------------------");
    //            
    List> collect2 = collect1.entrySet().stream().filter(userLongEntry -> userLongEntry.getValue() > 1).collect(Collectors.toList());
    collect2.forEach(System.out::println);
    
  • (4)実戦
  • //A      B,C。
    //B     A,C,D,E,F
    //C      A,B,D,F
    //   A          (  A     ,   A   2         )
    Student studentA = new Student("A", new String[]{"B", "C"});
    Student studentB = new Student("B", new String[]{"A", "C", "D", "E", "F"});
    Student studentC = new Student("C", new String[]{"A", "B", "D", "F"});
    List students = new ArrayList<>();
    students.add(studentA);
    students.add(studentB);
    students.add(studentC);
    
    //1、    A     ["B","C"]
    Stream a = students.stream().filter(student -> student.getName().equals("A")).map(student -> student.getFriend());
    List collect = a.collect(Collectors.toList());
    Stream stringStream = collect.stream().flatMap(strings -> Stream.of(strings));
    List friendA = stringStream.collect(Collectors.toList());
    
    //2、  A       ["A","C","D","E","F"],["A","B","D","F"]
    Stream studentStream = students.stream().filter(student -> friendA.stream().anyMatch(s -> s.equals(student.getName())));
    Stream stream = studentStream.map(student -> student.getFriend());
    List collect1 = stream.collect(Collectors.toList());
    
    //3、       ["A","C","D","E","F","A","B","D","F"]
    Stream stringStream1 = collect1.stream().flatMap(strings -> Stream.of(strings));
    List collect2 = stringStream1.collect(Collectors.toList());
    
    //4、  A   A   ["D","E","F","D","F"]
    Stream a1 = collect2.stream().filter(s -> !(s.equals("A") || friendA.stream().anyMatch(s1 -> s1.equals(s))));
    List collect3 = a1.collect(Collectors.toList());
    System.out.println(collect3);
    
    //5、            
    Map collect4 = collect3.stream().collect(Collectors.groupingBy(o -> o, Collectors.counting()));
    System.out.println(collect4);
    

    3.インタフェースの新規作成:デフォルト方法と静的方法
    関数インタフェース(注記:@FunctionalInterface)は、Lambda式でインタフェースのオブジェクトを作成できます.カスタム抽象メソッドのインタフェースが1つしか含まれていません.Objectクラスのequals抽象メソッドでも、default、staticで修飾された独自のメソッドボディでも、同じdefaultメソッドのインタフェースが複数実装されている場合は、defaultメソッドを書き換える必要があります.
    関数インタフェース
    パラメータタイプ
    戻りタイプ
    用途
    java.util.function.Consumer
    T
    void
    タイプTのオブジェクトに操作を適用し、方法void accept(T t)を含む.【消費型】
    java.util.function.Supplier
    なし
    T
    メソッドT get()を含むタイプTのオブジェクトを返します.【供給型】
    java.util.function.Function
    T
    R
    パラメータタイプT、戻りタイプR、メソッドR apply(T t)を含む;【関数型】
    java.util.function.Predicate
    T
    boolean
    パラメータタイプTは、メソッドboolean test(T)を含むタイプbooleanを返す.【断言型】
        /**
         *     :         
         *  default                           ,         
         *  (List   Iterable,           default forEach  )
         */
        @Test
        public void testDefaultFunctionInterface(){
            //         .               
            JDK8Interface1.staticMethod();
            //                    
            new JDK8InterfaceImpl1().defaultMethod();
            //    ,           
            new JDK8InterfaceImpl2().defaultMethod();
        }
        //@FunctionalInterface
    public interface JDK8Interface1 {
    
        //1.            
        public static void staticMethod(){
            System.out.println("        ");
        }
        
        //2.  default                
        public default void defaultMethod(){
            System.out.println("        ");
        }
    
    //    public abstract void add();
    }
    
    public interface JDK8Interface2 {
    
        //            
        public static void staticMethod(){
            System.out.println("        ");
        }
        //  default                
        public default void defaultMethod(){
            System.out.println("        ");
        }
    }
        public class JDK8InterfaceImpl1 implements JDK8Interface1 {
            //     ,            ,  /     !
    //        @Override
    //        public void defaultMethod(){
    //            System.out.println("        ");
    //        }
        }
        
        public class JDK8InterfaceImpl2 implements JDK8Interface1,JDK8Interface2 {
            //     ,       ,        
            @Override
            public void defaultMethod() {
                //   
                JDK8Interface1.super.defaultMethod();
                System.out.println("           !!!!");
            }
        }
    

    4.メソッド参照、Lambda式との併用
    実はlambdaの略写で、中間関数式インタフェースはコンテキストの作用だけを果たして、直接省くことができて、直接関数式インタフェースの具体的な実現を書いて、使用方法の引用の方式
    public void testMethodReference(){
        //     。   Class::new,      Class< T >::new,            ;
        final Car car = Car.create( Car::new );
        final List< Car > cars = Arrays.asList( car );
        //      。   Class::static_method,      Class     ;
        cars.forEach( Car::collide );
        //         。     Class::method。  ,      ;
        cars.forEach( Car::repair );
        //         ,     instance::method。  ,          ,           ;
        final Car police = Car.create( Car::new );
        cars.forEach( police::follow );
    }
    
    public static class Car {
        public static Car create( final Supplier< Car > supplier ) {
            System.out.println("        ");
            return supplier.get();
        }              
             
        public static void collide( final Car car ) {
            System.out.println( "       " + car.toString() );
        }
             
        public void repair() {   
            System.out.println( "          " + this.toString() );
        }
        
        public void follow( final Car car ) {
            System.out.println( "          " + car.toString() );
        }
    }
    

    5.重複注釈の導入
    同じタイプ(クラス、プロパティ、またはメソッド)を明示する前に、同じタイプの注釈を複数回使用できます.
    @Filters({@Filter(  value="filter1",value2="111" ),@Filter(  value="filter2", value2="222")})
    --     -->
    @Filter( value="filter1",value2="111" )
    @Filter( value="filter2", value2="222")
    

    6.タイプ注記
    ElementType列挙にTYPEが追加されました.PARAMETER、TYPE_@Target(ElementType_TYPE_USE)を使用して注釈定義を修飾できるように、USEの2つの列挙値があります.この注釈はタイプ注釈と呼ばれ、タイプに使用できる場所で使用できます.
    TYPE_PARAMETER:この注釈がタイプパラメータの宣言文に書けることを示します.タイプパラメータ宣言:
    TYPE_USE:注釈は、a.オブジェクトを作成する(newキーワードで作成する)b.タイプ変換c.implementsを使用してインタフェースを実装するd.throwsを使用して例外を宣言するなど、任意のタイプの場所で使用できることを示します.
    7.最新のDate/time API(JSR 310)
    //1.Clock
    final Clock clock = Clock.systemUTC();
    System.out.println( clock.instant() );//2020-12-24T07:32:56.132Z
    System.out.println( clock.millis() );//1608795176247
    
    //2. ISO-8601             
    final LocalDate date = LocalDate.now();
    final LocalDate dateFromClock = LocalDate.now( clock );
             
    System.out.println( date );//2020-12-24
    System.out.println( dateFromClock );//2020-12-24
             
    // ISO-8601             
    final LocalTime time = LocalTime.now();
    final LocalTime timeFromClock = LocalTime.now( clock );
             
    System.out.println( time );//15:32:56.257
    System.out.println( timeFromClock );//15:32:56.257
    
    // 3.ISO-8601             
    final LocalDateTime datetime = LocalDateTime.now();
    final LocalDateTime datetimeFromClock = LocalDateTime.now( clock );
             
    System.out.println( datetime );//2020-12-24T15:32:56.257
    System.out.println( datetimeFromClock );//2020-12-24T15:32:56.257
    
    // 4.       /  ,
    final ZonedDateTime zonedDatetime = ZonedDateTime.now();
    final ZonedDateTime zonedDatetimeFromClock = ZonedDateTime.now( clock );
    final ZonedDateTime zonedDatetimeFromZone = ZonedDateTime.now( ZoneId.of( "America/Los_Angeles" ) );
             
    System.out.println( zonedDatetime );//2020-12-24T15:32:56.258+08:00[Asia/Shanghai]
    System.out.println( zonedDatetimeFromClock );//2020-12-24T07:32:56.258Z
    System.out.println( zonedDatetimeFromZone );2020-12-23T23:32:56.260-08:00[America/Los_Angeles]
    
    //5.             
    final LocalDateTime from = LocalDateTime.of( 2014, Month.APRIL, 16, 0, 0, 0 );
    final LocalDateTime to = LocalDateTime.of( 2015, Month.APRIL, 16, 23, 59, 59 );
     
    final Duration duration = Duration.between( from, to );
    System.out.println( "Duration in days: " + duration.toDays() );//365
    System.out.println( "Duration in hours: " + duration.toHours() );//8783
    

    8.base 64復号APIの追加
    final String text = "        !!abjdkhdkuasu!!@@@@";
    String encoded = Base64.getEncoder().encodeToString( text.getBytes( StandardCharsets.UTF_8 ) );
    System.out.println("   ="+ encoded );
    
    final String decoded = new String(Base64.getDecoder().decode( encoded ),StandardCharsets.UTF_8 );
    System.out.println( "   ="+decoded );
    

    9.配列並列(parallel)操作
    long[] arrayOfLong = new long [ 20000 ];        
    //1.       
    Arrays.parallelSetAll( arrayOfLong, 
        index -> ThreadLocalRandom.current().nextInt( 1000000 ) );
    //2.    10   
    Arrays.stream( arrayOfLong ).limit( 10 ).forEach( 
        i -> System.out.print( i + " " ) );
    System.out.println();
    //3.    
    Arrays.parallelSort( arrayOfLong );     
    //4.       10   
    Arrays.stream( arrayOfLong ).limit( 10 ).forEach( 
        i -> System.out.print( i + " " ) );
    System.out.println();
    

    10.JVMのPermGenメソッド領域が削除されました.代わりにMetaspace(JEP 122)メタ空間が削除されました.
    -XX:MetaspaceSize      ,                  ,  GC        
    -XX:MaxMetaspaceSize    ,       
    -XX:MinMetaspaceFreeRatio GC  ,   Metaspace          ,               
    -XX:MaxMetaspaceFreeRatio GC  ,   Metaspace          ,               
    

    関連記事リンク:<<<<<<<<<<<<<<<<<<