반응형
    
    
    
  stream API
public class ForIterationExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        for (int i = 0; i < integerList.size(); i++) {
            System.out.println(integerList.get(i));
        }
    }
}-> stream API 를 사용하지 않을 때. for 의 iterator 를 사용할 때
- 기존의 for, if 문을 대체할 수 있다.
- for 와 달리 forEach 를 쓰기때문에, 인덱스를 알 수 없다. (사실 알게할 수는 있는데, 가독성이 매우 떨어지게된다.)
- for 와 달리 break 가 없다. (filter() 를 사용하면 break 가능)
 
- Collection 인터페이스를 상속받은 클래스들에서 stream 을 사용 가능하다. (ArrayList, HashSet, etc)
- Map 인터페이스를 상속받은 클래스들에서는 우회해서 사용 가능하다.(HashMap, etc)
forEach - 반복시키기
public class ForEachIterationExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        integerList.stream().forEach(integer -> {
            System.out.println(integer);
            if(integer.equals(40)) {
                throw new RuntimeException();
            }
        });
    }
}
filter - 조건에 맞는 요소만 뽑기
public class ForAndIfFilterExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        Integer findNumber = null;
        for (int i = 0; i < integerList.size(); i++) {
            System.out.println(integerList.get(i));
            if(integerList.get(i).equals(40)) {
                findNumber = integerList.get(i);
                break;
            }
        }
        System.out.println("findNumber=" + findNumber);
    }
}-> for 에서 조건에 맞는 분기를 if 로 찾고있다.
public class FilterExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        Integer findNumber = integerList.stream().filter(integer -> {
            System.out.println(integer);
            if(integer.equals(40))
                return true;
            return false;
        }).findAny().get();
        System.out.println("findNumber=" + findNumber);
    }
}
-> 조건에 맞지 않는 분기는 return false 한다.
-> filter 에서 조건에 맞는 분기는 return true 하고 있다.
-> .findAny() 해서 하나를 찾자마자 filter 가 종료된다. (for 에서 break 와 같은 효과)
map - 요소를 매핑시키기
interface 의 map 이 아니다. stream API 의 map 메서드를 말한다.
map 메서드는 원래의 Collection 에서 특정한 연산을 적용하여 새로운 Collection 을 만든다.
public class ForMapExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        List<Integer> x10IntegerList = new ArrayList<>();
        for (int i = 0; i < integerList.size(); i++) {
            x10IntegerList.add(integerList.get(i) * 10);
        }
        System.out.println(x10IntegerList);
    }
}
public class MapExampleMain {
    public static void main(String[] args) {
        List<Integer> integerList = new ArrayList<>();
        integerList.add(10);
        integerList.add(20);
        integerList.add(30);
        integerList.add(40);
        integerList.add(50);
        integerList.add(60);
        integerList.add(70);
        List<Integer> x10IntegerList = integerList.stream()
                .map(integer -> integer * 10)
                .toList();
        System.out.println(x10IntegerList);
    }
}
위 두 코드는 정확하게 같은 동작을 한다.
map() 에서는 람다식을 파라미터로 전달받는데, 1 line 짜리 람다식은 중괄호가 {} 생략 가능하다.
filter와 map의 결합
public class FilterAndMapExampleMain {
    public static void main(String[] args) {
        int[] integerArray = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
        List<Integer> integerList = Arrays.stream(integerArray)
                .boxed()
                .toList();
        System.out.println(integerList);
        List<Integer> evenNumberList = integerList.stream()
                .filter(integer -> integer % 2 == 0)
                .toList();
        System.out.println(evenNumberList);
        List<Integer> evenX10NumberList = evenNumberList.stream()
                .map(integer -> integer * 10)
                .toList();
        System.out.println(evenX10NumberList);
    }
}-> list 에서 짝수만 뽑아와서 데이터를 모두 10배씩 해서 새로운 list 를 만드는 과정
List<Integer> evenX10NumberList = integerList.stream()
                .filter(integer -> integer % 2 == 0)
                .map(integer -> integer * 10)
                .toList();-> 이렇게 filter() 와 map() 을 합칠 수 있다.
for + if 의 조합에 비해서 가독성이 얼마나 좋은가!
stream 을 잘 다루는 것은 자바 개발자에게 엄청난 무기가 되겠다.
map 에 stream API 사용하기
앞에서 말했던 것처럼 map 은 Collection 인터페이스를 상속받지 않고,
독자적인 인터페이스를 상속받기 때문에 stream API 를 사용할 수 없다.
하지만 map 을 set 으로 변환시켜서 stream API 를 사용할 수 있다.
public class MapStreamExample {
    public static void main(String[] args) {
        Map<String, Integer> someMap = new HashMap<>();
        Set<Map.Entry<String, Integer>> entries = someMap.entrySet();
        Set<String> keySet = someMap.keySet();
        List<Integer> valueList = someMap.values().stream().toList();
        entries.stream().forEach(stringIntegerEntry -> {
            String key = stringIntegerEntry.getKey();
            Integer value = stringIntegerEntry.getValue();
            // key, value 사용
        });
    }
}반응형
    
    
    
  'Programming Language > Java' 카테고리의 다른 글
| [Java] 객체 지향 프로그래밍의 5가지 기본 원칙 SOLID 를 예제와 함께 알아 보자. (1) (0) | 2023.09.27 | 
|---|---|
| [Java] stream API 와 Optional (0) | 2023.09.26 | 
| [Java] if문이 너무 많다면, 리팩토링을 해보자. (0) | 2023.09.25 | 
| [Java] Optional - nullPointException을 잘 다뤄보자. (0) | 2023.09.25 | 
| [Java] Object 클래스와 주요 메서드 - equals(), hashCode(), toString() (0) | 2023.09.22 |