만족은 하되 안주하지는 말자

기록해야 기억한다

프로그래밍/JAVA

[Java] Optional 에 대해 알아보자 - 2

D36choi 2021. 4. 21. 15:03
728x90

2021.03.29 - [프로그래밍/JAVA] - [Java] Optional 에 대해 알아보자 - 1

 

[Java] Optional 에 대해 알아보자 - 1

Optinal class 는 자바 8에서 도입된 주요 기술 중 하나입니다. 이 클래스의 목적은 null 대신에 optional한 (있거나 없을 수 있는) 값을 표현하기 위한 해결책을 제공하는 것입니다. 기본 Optional 객체 생

choichumji.tistory.com

 


 

filter() 를 활용한 조건부 리턴

Optional 의 filter 메서드를 활용하면, null check 와 함께 복잡한 조건문을 하나의 라인으로 축약하기 쉽다.  

 

예를 들어, 사람마다 키를 재서 120cm ~ 190cm 인 경우에 롤러코스터를 탈 수 있는지 없는지를 판단하는 메서드를 작성한다고 가정하자.

 

package com.demo.ssedemo.optional;

import org.junit.jupiter.api.Test;

import java.util.Optional;

import static org.assertj.core.api.Assertions.assertThat;

public class optionalTest {


    public static class Person {

        private Integer height;
        
        public Person(Integer height) {
            this.height = height;
        }

        public int getHeight() {
            return height;
        }
    }

    @Test
    public void isInRange() {

		assertThat(isPossibleToTakeRollerCoaster(new Person(160))).isTrue();
        assertThat(isPossibleToTakeRollerCoaster(new Person(110))).isFalse();
        assertThat(isPossibleToTakeRollerCoasterWithFilter(new Person(160))).isTrue();
        assertThat(isPossibleToTakeRollerCoasterWithFilter(new Person(200))).isFalse();
        assertThat(isPossibleToTakeRollerCoasterWithFilter(null)).isFalse();

    }

	// 아래 메소드 2개를 넣는 위치
}

 

Person 이라는 정적 클래스를 정의하고 해당 사람의 키를 멤버 변수로 두었다.

 

위 테스트의 3가지 케이스가 통과되기 위해서는 몇가지 조건을 통과해야한다.

 

getter 를 통해 키를 가져와서 키가 롤러코스터를 타기에 적합한지, 그리고 isPossibleToTakeRollerCoaster method 에 Person 객체가 null 이 아닌지도 체크해줘야 한다.

 

filter 없이 일반적인 조건문

    public boolean isPossibleToTakeRollerCoaster(Person person) {

        boolean isPossible = false;
        if (person != null &&
            person.getHeight() > 120 &&
            person.getHeight() < 190) {
            isPossible = true;
        }

        return isPossible;
    }

일반적인 경우에는 이처럼 if문을 통해 null 인지를 검사하고, getter 메서드를 통해 키를 가져와서 true of false 를 검사할 것이다.

 

만약 filter 와 Optional 을 활용한다면 이렇게 변할 수 있을 거다.

 

filter 를 활용한 경우

    public boolean isPossibleToTakeRollerCoasterWithFilter(Person person) {

        return Optional.ofNullable(person).map(Person::getHeight)
            .filter(h -> h > 120)
            .filter(h -> h < 190)
            .isPresent();
    }

일단 조건문에 대해서 흐름이 잘 읽힌다는 (이것도 사람마다 다르겠지만) 장점이 있어보인다.

그리고 getter 를 여러번 명시하지도, 따로 변수를 여러개 선언하지도 않고도 조건들을 처리할 수 있다는 것도 체감된다.

 

 

map method 는 어떤 값을 다른 형태의 값으로 바꿀 때 보통 사용한다. (원래 값에는 영향을 미치지 않는다)

 

 

이렇게 바꾸면 얻는 장점이 뭔데?

 

역시나 이런 Optional.filter() 를 활용하는 경우 가장 큰 장점은

개발이 길어지고 복잡해지다보면 개발자가 놓칠 수 있는 null check 에 대해 Optional 이 알아서 해준다는 점이다.

 

런타임 에러는 개발자가 코드를 작성할 때 놓치기 쉬운데, 이런 변수들을 Optional 로 포장하는 버릇을 들인다면 당황스러운 일이 생길 확률이 훨씬 낮아질 것이다.