Kotlin

[Kotlin] lateinit과 by lazy의 차이점

꾸준함. 2022. 7. 13. 04:16

개요

회사와 연계해서 진행하는 패스트캠퍼스 코틀린 안드로이드 강의를 듣는 도중 생소한 개념인 lateinit과 by lazy 키워드가 등장했습니다.

다행히 holika님이 잘 정리해주신 글이 있어 개념은 이해할 수 있었지만 아직 정확한 사용처는 파악하지 못했습니다.

프로젝트를 진행하면서 사용하는 케이스가 나왔을 때 해당 게시글에 추가 작성하도록 하겠습니다.

 

https://holika.tistory.com/entry/%EB%82%B4-%EB%A7%98%EB%8C%80%EB%A1%9C-%EC%A0%95%EB%A6%AC%ED%95%9C-Kotlin-lateinit%EA%B3%BC-by-lazy%EC%9D%98-%EC%B0%A8%EC%9D%B4%EC%A0%90

 

[내 맘대로 정리한 Kotlin] lateinit과 by lazy의 차이점

늦은 초기화 가끔 클래스 안에서 '내가 이 변수를 쓸 것이다'라고 선언만 해 놓고, 나중에 값을 사용할 수 있게 되면 그 때 값을 입력해 주고 싶을 때가 있다. 이럴 때 사용 가능한 방법 중에는 아

holika.tistory.com

 

1. lateinit과 bylazy를 사용하는 이유

holika님에 의하면 lateinit과 bylazy는 클래스 변수 중 생성할 때는 쓰이지 않고 나중에 쓰이는 변수에 대해 적용하는 키워드라고 합니다.

lateinit과 bylazy가 사용되는 케이스는 아래와 같습니다. 

  • x의 값이 변할 수 있지만, 절대 null이어서는 안 되는 경우 (처음에 nullable 한 객체로 초기화해주는 것이 부적절한 경우)
  • x의 값이 처음 한 번만 정해지면 다시는 변하지 않는 경우 (java의 final, c++의 const와 같이)

 

* 제가 이해한 바로는 JPA의 Lazy Loading과 유사한 느낌이었습니다.

* JPA의 경우 Lazy Loading을 하지 않을 경우 N + 1 쿼리 문제가 발생하기 때문에 반드시 필요한 기능이지만 코틀린에서 변수 값을 초기에 NULL로 설정했다가 나중에 바꾼다고 해서 성능 이슈가 발생할 것 같지 않은데 왜 이 두 키워드가 존재하는지 와닿지는 않습니다.

 

2. lateinit

lateinit 키워드가 var 앞에 붙게 되면 해당 변수는 절대 null이 될 수 없습니다.

x에 값이 설정되기 전에는 null이 아닌 uninitialized 형태로 존재하며 초기화되지 않은 상태에서 변수를 사용하려고 할 경우 에러가 발생합니다.

따라서, 해당 키워드를 변수에 부여했을 경우 반드시 초기화 단계를 거쳐야 합니다.

 

주의: lateinit의 경우 Int, Long, Double, Float와 같은 Primitive Type에 대해서 사용 불가


 

3. by lazy

by lazy의 경우 해당 변수가 나중에 사용될 경우 어떤 값이 들어가는지 변수를 선언함과 동시에 초기화를 진행합니다.

그리고 lateinit과의 차이점은 lateinit의 경우 var 변수에 적용되므로 값 변경이 가능하지만 by lazy의 경우 val 변수에 적용하기 때문에 한번 초기화된 값 외 다른 값으로 변경할 수 없습니다.

by lazy가 사용되는 코드는 holika님이 잘 정리해주셨는데 아래와 같습니다.


 

위 코드의 경우 x는 inputValue라는 문자열의 길이를 받아와야 하는데 inputValue가 아직 초기화가 되지 않은 상태이므로 바로 길이를 저장할 수 없는 상태입니다.

따라서, 나중에 inputValue가 제대로 값을 가지게 된 이후 x를 활용하기 위해  by lazy 키워드를 적용했습니다.

 

* 사실 이 부분도 inputValue를 초기화한 이후 별도 변수를 선언하여 길이를 저장해도 되지 않을까?라는 의문이 생기기는 합니다.

 

정리

실제로 어디서 사용되는지는 의문이지만 코틀린의 lateinit과 by lazy 키워드에 대해 알아봤습니다.

lateinit의 경우 var 변수에 적용되고, by lazy는 val 변수에 적용이 되는 키워드입니다.

따라서, 초기화한 뒤에도 값이 변할 수 있는 변수에 대해서는 lateinit을 적용하고 한번 초기화한 이후에는 read-only로 사용할 변수에 대해서는 by lazy를 적용하면 될 것 같습니다.

 

참고

https://holika.tistory.com/entry/%EB%82%B4-%EB%A7%98%EB%8C%80%EB%A1%9C-%EC%A0%95%EB%A6%AC%ED%95%9C-Kotlin-lateinit%EA%B3%BC-by-lazy%EC%9D%98-%EC%B0%A8%EC%9D%B4%EC%A0%90

 

[내 맘대로 정리한 Kotlin] lateinit과 by lazy의 차이점

늦은 초기화 가끔 클래스 안에서 '내가 이 변수를 쓸 것이다'라고 선언만 해 놓고, 나중에 값을 사용할 수 있게 되면 그 때 값을 입력해 주고 싶을 때가 있다. 이럴 때 사용 가능한 방법 중에는 아

holika.tistory.com

 

반응형