코틀린 표준 라이브러리에서 제공하는 Scope Functions 있습니다.
지금부터 Scope Functions 에 대해 알아보고,
각각 어떻게 활용하는지 예시를 통해서 확인하려고 합니다.
1. Scope Functions 개요
Scope function 은 어떤 객체에 대한 코드 블록을 만들고 실행시킵니다.
이때, 블록 내 객체에 접근하기 쉬우며 특정 값을 return 하기도 한다는 특징을 가집니다.
대표적인 함수로 let, run, apply, also 가 있습니다.
2. Scope Functions 왜 사용해야 될까요?
Scope Function 이 가지는 특징은 바로 코드의 간결성과 가독성으로 이어집니다.
Scope Functions 을 사용했을 때와 사용하지 않은 예시를 통해 바로 확인해보겠습니다.
(1) Scope Function 사용 안 했을 때
val alice = Person("Alice", 20, "Amsterdam")
alice.moveTo("London")
alice.incrementAge()
(2) Scope Function 사용했을 때
Scope function let 을 통해서 person 객체에 대한 코드 블록을 만들어주고,
전달 받은 it(person) 을 통해 쉽게 객체에 접근하는 것을 확인할 수 있습니다.
Person("Alice", 20, "Amsterdam").let {
it.moveTo("London")
it.incrementAge()
}
결과적으로 특정 객체에 대한 코드블록은 가독성을 높여줄 수 있고,
3. Scope Functions 활용
이제 Scope Functions 을 어떻게 활용해야 할지 고민이 필요합니다.
이들은 매우 유사한 기능을 가지고 있기 때문에 각각의 차이점을 인지하는게 중요한데요,
대표적으로 let, run, apply, also 각각 함수별로 객체 참조 방법, 리턴값, 예시 를 살펴보려고 합니다.
♣ let
- 객체 참조 방법 : it
- 리턴값 : lamda result
- 예시 : 코드블록 내에서 참조되는 객체를 non-null 값으로 만들때 (safe operator=?. 를 계속 호출하지 않아도됨)
private fun printlnPersonInformation(person: Person?) {
var nameLength: Int?
// sope function 사용 안함
println(person?.name)
println(person?.age)
println(person?.location)
nameLength = person?.name?.length
println(nameLength)
// let 사용 (return 사용O)
nameLength = person?.let {
println(it.name)
println(it.age)
println(it.location)
it.name.length
}
println(nameLength)
// let 사용 (return 사용X)
person?.let {
println(it.name)
println(it.age)
println(it.location)
println(it.name.length)
}
}
♣ run
- 객체 참조 방법 : this
- 리턴값 : lamda result
- 예시 : 특정 객체에 대한 작업(process) 을 담고, 필요한 결과 뽑을 때
val numbers = mutableListOf("one", "two", "three")
var countEndsWithE: Int
// scope function 사용 안함
numbers.add("four")
numbers.add("five")
countEndsWithE = numbers.count { it.endsWith("e") }
println("There are $countEndsWithE elements that end with e.")
// run 사용
countEndsWithE = numbers.run {
add("four")
add("five")
count { it.endsWith("e") }
}
println("There are $countEndsWithE elements that end with e.")
♣ apply
- 객체 참조 방법 : this
- 리턴값 : context object
- 예시 : 객체 초기화할 때
var persons: ArrayList<Person> = ArrayList()
// scope function 사용 안함
persons.add(Person("Alice", 20, "Amsterdam"))
persons.add(Person("adam", 30, "London"))
println(persons)
// apply 사용
persons = ArrayList<Person>().apply {
add(Person("Alice", 20, "Amsterdam"))
add(Person("adam", 30, "London"))
}
println(persons)
♣ also
- 객체 참조 방법 : it
- 리턴값 : context object
- 예시 : 부가작업이 필요할 때
// Scope function 사용 안함
val value = Random().nextInt(100)
println("getRandomInt() generated value $value")
// also 사용
Random().nextInt(100).also {
println("getRandomInt() generated value $it")
}
끝으로...
scope function 을 정리하면서 각 함수마다 유사한 기능을 가지고 있어
어떻게 이해하고 설명해야될까 고민이 많았던 것 같습니다.
공식문서랑 몇몇 블로그를 참조하여 이해하기 쉬운 예시를 만드는 부분에 집중한 것 같습니다.
끝까지 읽어주셔서 감사합니다:)
참고자료
안드로이드 뉴토피아 (블로그)
developer88 (블로그)
0 comments: