Java Lambda Expressions는 Java 8에서 도입 한 새로운 기능입니다. 시뮬레이션 된 기능 프로그래밍을위한 구문 설탕이라고 할 수 있습니다. 그들은 JavaScript의 폐쇄와 비슷하지만 다소 다릅니다. 주요 목적은 인코딩을 단순화하기 위해 기능 구문을 제공하는 것입니다.
람다 기본 구문
Lambda의 기본 구조는 (인수) -> 본문이며 몇 가지 상황이 있습니다.
신체에는 {}에 진술이 포함되어야하며 진술이 하나만있을 때 {}를 생략 할 수 있습니다.
일반적인 작문 방법은 다음과 같습니다.
(a) -> a * a
(int a, int b) -> a + b
(a, b) -> {return a -b;}
() -> system.out.println (Thread.currentThread (). getId ())
FunctionalInterface
개념
Java Lambda 표현식은 기능적 인터페이스를 기반으로합니다. 기능 인터페이스 란 무엇입니까? 간단히 말해서 하나의 메소드 (함수) 만있는 인터페이스입니다. 이 유형의 인터페이스의 목적은 단일 작업에 대한 것이며, 이는 단일 기능과 동일합니다. Runnable 및 비교기와 같은 일반적인 인터페이스는 기능적 인터페이스이며 @functionalInterface로 주석이 달라집니다.
예를 들어보세요
스레드를 예로 사용하는 것은 쉽게 이해하기 쉽습니다. 실행 가능한 인터페이스는 스레드의 실행되는 로직 인 메소드 void run ()을 포함하는 프로그래밍을 스레드 할 때 일반적으로 사용되는 인터페이스입니다. 이전 구문에 따르면, 우리는 일반적으로 실행 가능한 익명 클래스를 사용하여 다음과 같이 새 스레드를 만듭니다.
new Thread (new Runnable () {@override public void run () {System.out.println (thread.currentThread (). getId ());}}); start ();너무 많이 쓰면 지루하지 않습니까? Lambda를 기반으로하는 작문 규칙은 다음과 같이 간결하고 명확 해집니다.
새 스레드 (() -> system.out.println (Thread.currentThread (). getId ()). 시작 ();
스레드의 매개 변수에주의하십시오. Runnable의 익명 구현은 한 문장으로 구현되며 더 잘 이해하기 위해 다음과 같은 것으로 작성되었습니다.
runnable r = () -> system.out.println (Thread.currentThread (). getId ());
새 스레드 (r) .start ();
물론 Lambda의 목적은 간결하게 글을 쓰는 것이 아니라 이해 후 더 높은 수준의 목적을 요약하는 것입니다.
비교기의 또 다른 예를 살펴 보겠습니다. 전통적인 작문 방법에 따라 다음과 같이.
integer [] a = {1, 8, 3, 9, 2, 0, 5}; arrays.sort (a, new 비교기 <integer> () {@override public int comperm (Integer O1, Integer O2) {return o1 -o2;}});람다 표현식은 다음과 같이 작성됩니다.
정수 [] a = {1, 8, 3, 9, 2, 0, 5};
arrays.sort (a, (O1, O2) -> O1 -O2);
JDK의 기능적 인터페이스
기존 클래스 라이브러리가 Lambda 표현식을 직접 사용하기 위해서는 Java 8에 기능적 인터페이스로 표시된 일부 인터페이스가있었습니다.
새로운 패키지 java.util.function이 Java 8에 추가되어 일반적으로 사용되는 기능 인터페이스를 제공합니다.
또한 BooleanSupplier, DoublebinaryOperator, DoubleConsumer, Doublefunction <R>, DoublePredicate, DoublesUpplier, DoubleTointFunction, DoubleTolOntfunction, DoubleTolongfunction, DoubleAnaryOperator, IntbinaryOperator, Intfuneter, Intfunerer, Intfuneger, Intfuneter, Intbinater forctunction을 포함한 기본 유형의 처리에보다 구체적인 기능이 추가됩니다. intpredicate, intsupplier, inttodoubleftunction, inttolondfunction, intunaryoperator, longbinary -opremerator, longconsumer, longfunction <r>, longpredicate, longsupplier, longtodoublefunction, longtointfunction, longunaryoperator, todoublebifunction <t, u>, TodoubleFunction <t>, ToIntBifunction <T, U>, ToIntFunction <t>, TolonGbifunction <T, U>, TolOngFunction <t>. 위의 기능 인터페이스와 결합하여 이러한 기본 기능 인터페이스의 클래스 이름을 통해 인터페이스의 역할을 볼 수 있습니다.
기능 인터페이스를 만듭니다
때때로 우리는 기능 인터페이스를 직접 구현해야 하며이 방법은 매우 간단합니다. 먼저이 인터페이스에 하나의 기능 작동 만 수행 한 다음 인터페이스 유형에 @functionalInterface를 주석을 달 수 있는지 확인해야합니다.
유형 파생
유형 파생은 Lambda 표현의 기초이며, 유형 파생 과정은 Lambda 표현의 편집 과정입니다. 다음 코드는 예입니다.
함수 <string, integer> strtoint = str-> integer.parseint (str);
편집하는 동안 내가 이해하는 유형 파생 과정은 다음과 같습니다.
여기의 대상 유형은 키이며, 메소드 서명은 대상 유형을 통해 얻은 다음 Lambda 표현식과 비교합니다.
메소드 참조
메소드 참조 (메소드 참조)의 기초는 또한 기능적 인터페이스로, 기능적 인터페이스로 직접 구현할 수 있으며 Lambda 표현식과 동일한 함수를 가지며 유형 파생에 의존합니다. 메소드 참조는 하나의 방법 만 호출하는 람다 표현식의 단순화로 볼 수 있습니다.
메소드에 의해 참조 된 구문은 다음과 같습니다. type :: methodName 또는 InstanCename :: MethodName이며 생성자에 해당하는 메소드 이름은 새입니다.
예를 들어, 예제는 위에서 사용되었습니다.
함수 <string, integer> strtoint = str-> integer.parseint (str);
해당 방법 참조는 다음과 같습니다
함수 <문자열, 정수> strtoint = 정수 :: parseint;
메소드 유형에 따라 메소드 참조는 주로 다음 유형으로 나뉩니다. 생성자 메소드 참조, 정적 메소드 참조, 인스턴스 메소드 참조, 인스턴스 유형에 대한 인스턴스 메소드 참조 등
생성자 메소드 참조
구문은 다음과 같습니다. type :: new. 예를 들어 다음 기능은 문자열을 배열로 변환하는 것입니다.
메소드 참조 쓰기
함수 <문자열, 정수> strtoint = 정수 :: new;
람다 글쓰기
함수 <string, integer> strtoint = str-> new Integer (str);
전통적인 글
function <string, integer> strtoint = new 함수 <문자열, integer> () {@override public integer apply (string str) {return new Intger (str); }};
배열 생성자 참조
구문은 다음과 같습니다. type [] :: new. 예를 들어 다음 기능은 지정된 길이의 문자열 배열을 구성하는 것입니다.
메소드 참조 쓰기
함수 <integer, string []> fixedArray = String [] :: new;
메소드 참조 쓰기
함수 <integer, string []> fixedArray = length-> 새 문자열 [길이];
전통적인 글
function <integer, string []> fixedArray = new 함수 <정수, String []> () {@override public String [] apply (integer length) {return new String [length]; }};정적 메소드 참조
구문은 다음과 같습니다. type :: new. 다음 함수는 문자열을 배열로 변환하는 데 사용됩니다.
메소드 참조 쓰기
함수 <문자열, 정수> strtoint = 정수 :: parseint;
람다 글쓰기
함수 <string, integer> strtoint = str-> integer.parseint (str);
전통적인 글
function <string, integer> strtoint = new 함수 <문자열, integer> () {@override public integer apply (String str) {return integer.parseint (str); }};인스턴스 메소드 참조 인스턴스
구문은 다음과 같습니다. Instancename :: MethodName입니다. 예를 들어, 다음 판단 기능은 주어진 이름이 목록에 존재하는지 여부를 결정하는 데 사용됩니다.
list <string> names = arrays.aslist (new String [] { "Zhang San", "Li Si", "Wang Wu"});
술어 <string> checknameexists = names :: contains;
System.out.println (CheckNameExists.test ( "Zhang San"));
System.out.println (CheckNameExists.test ( "Zhang Si"));
유형에 대한 인스턴스 메소드 참조
구문은 다음과 같습니다. type :: methodname입니다. 런타임 참조
함수 <string, integer> calcstrlength = string :: longth; system.out.println (compstrlength.apply ( "zhang san")); list <string> names = arrays.aslist (새 문자열 [] { "zhangsan", "lisi", "wangwu"}); string (stick :: println);
예를 들어, 다음 함수는 문자열을 배열로 분할하기 위해 분리기를 지정했습니다.
bifunction <String, String, String []> split = String :: split;
문자열 [] names = split.Apply ( "Zhangsan, Lisi, Wangwu", ",");
System.out.println (Arrays.toString (이름));
스트림 객체
개념
스트림이란 무엇입니까? 여기의 스트림은 IO의 입력 스트림 및 출력 스트림과 다릅니다. 스트림은 패키지 java.util.stream 패키지에 있으며 Java 8에 새로 추가됩니다. Stream은 직렬 병렬 집계 작업을 지원하는 요소 세트이며, 이는 컬렉션 또는 반복자의 향상된 버전으로 이해 될 수 있습니다. 집계 작업은 무엇입니까? 간단한 예를 들어, 일반적인 예는 평균, 최대, 최소, 합계, 정렬, 필터링 등이 포함됩니다.
스트림의 몇 가지 기능 :
단일 처리. 한 번의 처리가 완료되면 현재 스트림이 닫힙니다.
병렬 작업에서 스트림을 얻는 일반적인 방법을 지원합니다
컬렉션에서 얻으십시오
collection.stream ();
Collection.parallelStream ();
정적 공장
Array.Stream (배열)
stream.of (t…)
intstream.range ()
여기서는 스트림에 대한 간단한 소개 만 제공하며 아래에는 특정 응용 프로그램이 있습니다. 스트림과 람다 표현의 관계에 대해 이야기하고 싶다면 실제로는 특히 밀접한 관계가 없습니다. 람다 표현이 스트림 사용을 크게 촉진하는 것입니다. 람다 표현이 없으면 스트림을 사용하는 동안 많은 익명의 클래스가 생성 될 것이며, 이는 매우 어색합니다.
예를 들어보세요
다음 데모는 직원 객체와 직원 객체로 구성된 목록 객체에 따라 다릅니다.
공개 클래스 직원 {개인 문자열 이름; 개인 문자열 섹스; 사적인 int 연령; 공공 직원 (문자열 이름, 문자열 섹스, int age) {super (); this.name = 이름; this.sex = 섹스; this.age = age; } public String getName () {return name; } public String getSex () {return sex; } public int getage () {반환 연령; } @override public String toString () {StringBuilder builder = new StringBuilder (); builder.append ( "Employee {name ="). Append (name) .append ( ", sex ="). Append (sex) .append ( ", age ="). Append (age) .append ( "}"); return builder.tostring (); }} 목록 <직원> 직원 = New ArrayList <> (); Employees.add (신입 사원 ( "Zhang San", "Male", 25)); Employees.add (신입 사원 ( "Li Si", "Female", 24)); Employep.Add (신입 사원 ( "Wang Wu", "Female", 23)); Employees.add (신입 사원 ( "토요일", "남성", 22)); 직원 (신입 사원 ( "Sun Qi", "Female", 21)); Employee.add (신입 직원 ( "Liu Ba", "Male", 20));모든 직원을 인쇄하십시오
Collection은 개별 객체를 하나씩 작동 할 수있는 Foreach 방법을 제공합니다.
직원 .foreach (e-> system.out.println (e));
또는
Employep.Stream (). foreach (e-> system.out.println (e));
나이별로 정렬하십시오
Collections.SORT (EmployE, (E1, E2) -> e1.getage () -E2.GetAge ());
직원 .foreach (e-> system.out.println (e));
또는
Employep.Stream (). Sorted ((e1, e2) -> e1.getage () -e2.getage ()). foreach (e-> system.out.println (e));
가장 오래된 여성 직원을 인쇄하십시오
Max/Min은 지정된 분류 조건에서 가장 큰/Min 요소를 반환합니다
직원 MaxageFemaleemployee = EmployEle.Stream () .filter (e-> "여성".Equals (e.getSex ()) .max ((e1, e2) -> e1.getage () -e2.getage ())
20 세 이상의 남성 직원을 인쇄하십시오
기준을 충족하는 요소를 필터링합니다
Employep.Stream ()
.filter (e-> e.getage ()> 20 && "male".Equals (e.getSex ()))
.foreach (e-> system.out.println (e));
가장 오래된 남성 직원 두 명을 인쇄하십시오
한계 메소드는 제한된 요소를 가로 채립니다
Employep.Stream () .filter (e-> "male".Equals (e.getSex ()) .sorted ((e1, e2) -> e2.getage () -e1.getage ()) .limit (2) .foreach (e-> system.out.println (e));
모든 남성 직원의 이름을 인쇄, 사용, 별도
주어진 함수를 실행 한 후 새 스트림을 형성하려면 매핑됩니다.
문자열 maleemployeesnames = orployeps.stream () .map (e-> e.getName ()) .Collect (collectors.joining ( ",")); System.out.println (maleemployeesNames);
통계 정보
IntsummaryStatistics, DoublesumMaryStatistics, LongsumMaryStatistics에는 스트림의 요약 데이터가 포함되어 있습니다.
IntSummaryStatistics STAT = EmployEPLOY () stat.getmin ()); System.out.println ( "평균 연령 :" + stat.getaverage ());
요약
Lambda Expressions는 실제로 많은 코드를 줄이고 생산성을 향상시킬 수 있습니다. 물론, 단점이 있습니다. 당신이 익숙해지면, 나는 당신이 그것을 좋아할 것이라고 믿습니다. 모든 것이 양면을 가지고 있으며, 특히 팀에서 장단점의 균형을 맞추는 방법에 따라 다릅니다.
위는 Java8 Javalambda를 분류하는 정보입니다. 우리는 향후 관련 정보를 계속 추가 할 것입니다. 이 웹 사이트를 지원 해주셔서 감사합니다!