본문 바로가기

Java

FlatMap 사용

스트림의 스트림을 스트림으로 변환
Stream<String[]> -> Stream<Stream>

flatMap은 Array 또는 Object로 감싸져 있는 모든 원소를 단일 원소 스트림으로 반환해준다.
List 안의 요소에 Collection 값을 가지는 경우 flatMap을 이용하여 간단히 Collection 값을 가져올 수 있음.

 

테스트를 위해 다음과 같은 객체를 생성한다.

 

User Class

 
public class User {
 
    private String name;
    private int age;
 
    public User(String name, int age) {
        super();
        this.name = name;
        this.age = age;
    }
 
    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;
    }
}
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5text-decoration:none">Colored by Color Scripter

 

MobileGame Class

public class MobileGame {
 
    private String gameName;
    private ArrayList<User> userList;
 
    public MobileGame(String gameName, ArrayList<User> userList) {
        super();
        this.gameName = gameName;
        this.userList = userList;
    }
 
    public String getGameName() {
        return gameName;
    }
    public void setGameName(String gameName) {
        this.gameName = gameName;
    }
 
    public ArrayList<User> getUserList() {
        return userList;
    }
    public void setUserList(ArrayList<User> userList) {
        this.userList = userList;
    }
}
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5text-decoration:none">Colored by Color Scripter

flatMapMain Class - 테스트

List 객체에 MobileGame 이라는 객체를 add 한다.
  MobileGame 객체는 ArrayList 객체를 가진다.
List > MobileGame > User
List에서 flatMap을 이용하여 User 객체만 추출해보자.

public class flatMapMain {
 
    public static void main(String[] args) {
 
/* 1. List 선언 */
        List<MobileGame> mobileGameList = new ArrayList<>();
 
/* 2. List에 요소 추가 */
        ArrayList<User> userList1 = new ArrayList<>();
        userList1.add(new User("disman"24));
        userList1.add(new User("hehe"30));
        MobileGame m1 = new MobileGame("anipang", userList1);
        mobileGameList.add(m1);
 
        ArrayList<User> userList2 = new ArrayList<>();
        userList2.add(new User("cyber"33));
        MobileGame m2 = new MobileGame("portress", userList2);
        mobileGameList.add(m2);
 
       /* 3. flatMap을 이용하여 List에서 User 객체만 따로 뽑아보자. */
        List<User> userList = mobileGameList.stream()
                      .flatMap(v -> v.getUserList().stream()) // Stream<MobileGame> -> Stream<User>
                      .collect(Collectors.toList());
 
        userList.stream().forEach((u) -> {
            System.out.println("User Name : " + u.getName() + ", User Age : " + u.getAge());
 
            // Result
            //User Name : disman, User Age : 24
            //User Name : hehe, User Age : 30
            //User Name : cyber, User Age : 33
        });
    }
}
http://colorscripter.com/info#e" target="_blank" style="color:#e5e5e5text-decoration:none">Colored by Color Scripter

 

아래는 위와 같은 내용의 비슷한 예제이다.

class PersonVO {
 
    private String name;
    private int age;
    private ArrayList<String> hobbyList;
 
    public PersonVO(String name, int age, ArrayList<String> hobbyList) {
        super();
        this.name = name;
        this.age = age;
        this.hobbyList = hobbyList;
    }
    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 ArrayList<String> getHobbyList() {
        return hobbyList;
    }
    public void setHobbyList(ArrayList<String> hobbyList) {
        this.hobbyList = hobbyList;
    }
}

List 안의 요소에 Collection 값을 가지는 경우 flatMap을 이용하여 간단히 Collection 값을 가져올 수 있음.

         * List
         *    PersonVO
         *        String name
         *        int age
         *        ArrayList hobbyList

public class FlatMapInfo {
 
    public static void main(String[] args) {
 
        List<PersonVO> personList = new ArrayList<>();
        personList.add(new PersonVO("APPR_TYPE_AGREE_PARAL"1new ArrayList<>(Arrays.asList("a1""a2""a3"))));
        personList.add(new PersonVO("APPR_TYPE_APPR_INFM"2new ArrayList<String>() {
            {
                add("b1");
                add("b2");
            }
        }));
 
        // flatMap 미사용 : 반복문을 2번 사용하여 가져옴
        List<String> hobbyListOld = new ArrayList<>();
        for (PersonVO vo : personList) {
            for (String list : vo.getHobbyList()) {
                hobbyListOld.add(list);
            }
        }
 
        /*
         * flatMap 사용 : 반복문없이 사용(예제가 너무 간단하려 얼핏 비슷해 보이지만,
         *                복잡한 로직에서 가져와야 하는 경우 유용할것 같다.)
         */
        List<String> hobbyListNew = personList.stream()
                //.map(v -> v.getHobbyList()) // source 1
                //.flatMap(v -> v.stream()) // source 2
                .flatMap(v -> v.getHobbyList().stream()) // source1, 2를 사용한 것과 상동
                .collect(Collectors.toList());
 
    }
}