YOUNGJIN
자바의 정석 14장 (람다와 스트림) 본문
람다식은 사실 익명 클래스의 객체이다.
함수형 인터페이스: 오직 하나의 추상 메서드만 정의되 있는 인터페이스
람다함수가 포함된 익명 클래스는 함수형 인터페이스의 구현체여야 한다.
람다식 사용 전
Collections.sort(list,new Comparator<String>(){
public int compare(String s1,String s2){
return s2.compareTo(s1);
}
});
람다식 사용 후
Collections.sort(list,(s1,s2)->s2.compareTo(s1));
여기서 Comparator는 당연히 함수형 인터페이스이다.
외부변수를 참조하는 람다식
@FunctionalInterface
interface MyFunction{
void myMethod();
}
class Outer{
int val=10;
class Inner{
int val=20;
void method(int i){ //final int i
int val=30; //final int val=30;
i=10; //에러. 상수의 값을 변경할 수 없음.
MyFunction f=()->{
System.out.println("i:"+i); //변경불가능
System.out.println("val:"+val); //변경불가능
System.out.println("this.val:"+ ++this.val); //변경가능
System.out.println("Outer.this.val"+ ++Outer.this.val); //변경가능
};
f.myMethod();
}
}
}
미리 정의되있는 함수형 인터페이스
함수형 인터페이스 | 메서드 |
Runnable | void run() |
Supplier<T> | T get() |
Consumer<T> | void accept(T t) |
Function<T,R> | R apply(T t) |
Predicate<T> | boolean test(T t) |
UnaryOperator<T> | T apply(T t) |
BinaryOperator<T> | T apply(T t,T t) |
Function의 합성
Function<String,Integer> f=(s)->Integer.parseInt(s,16);
Function<Integer,String> g=(i)->Integer.toBinaryString(i);
Function<String,String> h=f.andThen(g);
Predicate의 결합
Predicate<Integer> p=i->i<100;
Predicate<Integer> q=i->i<200;
Predicate<Integer> r=i->i%2==0;
Predicate<Integer> notP=p.negate();
Predicate<Integer> all=notP.and(q).or(r);
System.out.println(all.test(150)); //true
메서드 참조
람다식이 하나의 메서드만 호출하는 경우에는 메서드 참조로 람다식을 간략히 할 수 있다.
종류 | 람다 | 메서드 참조 |
static메서드 참조 | (...x)->ClassName.method(...x) | ClassName::method |
인스턴드메서드 참조 | (obj, ...x)->obj.method(...x) | ClassName::method |
특정 객체 인스턴스메서드 참조 | (...x)->obj.method(...x) | obj::method(x) |
생성자의 메서드 참조
Supplier<Myclass> s=MyClass::new; //()->new MyClass();
Function<Integer,int[]> f=int[]::new; //x->new int[x];
스트림 만들기
//컬렉션
List<Integer> list=Arrays.asList(1,2,3,4,5);
Stream<Integer> stream1=list.stream();
//가변인자
Stream<Integer> stream2=Stream.of(1,2,3);
//배열
int[] arr={1,2,3};
IntStream stream3=Arrays.stream(arr);
Stream<Integer> stream4=stream3.boxed();
//특정 범위의 정수
IntStream stream5=IntStream.range(1,5);
스트림의 중간연산
스트림의 최종연산
Comparator.comparing과 Comparator.thenComparing
myStream.sorted(Comparator.comparing(Student::getBan)
.thenComparing(Comparator.naturalOrder())
.forEach(System.out::println);
Optional
Optional<String> opt1=Optional.of("abc");
Optional<String> opt2=Optional.ofNullable(null); //null일 가능성이 있을 때는 ofNullable 이용
String str1=opt1.get(); //null이면 예외발생
String str2=opt2.orElse(""); //null이면 ""가져옴
Optional.ofNullable("abc").ifPresent(System.out::println);
분할과 그룹화
//partitioningBy
Map<Boolean, List<Student>> stuBySex=stuStream
.collect(partitioningBy(Student::isMale));
List<Student> maleStudent=stuBySex.get(true);
LIst<Student> femaleStudent=stuBySex.get(false);
//groupingBy
Map<Integer,List<Student>> stuByBan=stuStream
.collect(groupingBy(Student::getBan));
스트림의 변환
'Study > Java' 카테고리의 다른 글
자바의 정석 13장 ( Thread ) (0) | 2023.01.18 |
---|---|
자바의 정석 12장 ( Generics, 열거형, Annotation ) (0) | 2023.01.15 |
자바의 정석 11장 ( Collection ) (0) | 2023.01.15 |
메소드 참조 (0) | 2023.01.13 |
자바의 정석 9장 ( java.lang 패키지와 유용한 클래스 ) (0) | 2023.01.11 |
Comments