let() 함수
let() 함수는 이 함수를 호출한 객체를 이어지는 함수 블록의 인자로 전달 합니다.
let() 함수를 사용하면 불필요한 변수 선언을 방지할 수 있습니다.
showToast 함수의 인자 값인 msg 객체가 let() 함수를 호출한 예입니다.
let() 함수를 통해서 이 함수를 호출한 msg 객체를 이어지는 함수 블록의 인자로 전달하여 간편하게 Toast 메세지를 띄울
수 있습니다.
apply() 함수
apply() 함수는 이 함수를 호출한 객체를, 이어지는 함수 블록의 리시버로 전달합니다.
처음에 리시버라는 단어에서 의문을 가졌습니다. ( 리시버가 그 리시버인가..? 무슨 말이지 ? ) 예를 통해 알아 보겠습니다.
안드로이드에서 TextView의 text와 color를 바꾸고 싶을 때가 있죠?
tv.text = "~~~"
tv.setTextColor(컬러값)
이렇게 텍스트뷰에 2번 접근해서 사용하는 것보다 더 편하게 apply() 함수를 사용해보겠습니다.
tv.apply {
text="~~~~"
setTextColor(컬러값)
}
현재는 2개의 값만 수정했지만, 이 외 수많은 속성에 접근할 때에 무척 편리하겠죠 !!
위의 예제에서 알 수 있듯이,
리시버란, 바로 이어지는 블록 내에서 메서드 및 속성에 바로 접근할 수 있도록 할 객체를 의미합니다.
(접근 제어자에 따라 접근 가능한 범위에 한함)
위의 문구는 https://www.androidhuman.com/lecture/kotlin/2016/07/06/kotlin_let_apply_run_with/에서
참조했습니다. ( 제가 학습하고있는 책의 저자 커니님 블로그입니다. )
apply ( 적용하다 ) 즉 저는, apply()함수를 해당 객체를 계속해서 적용한다는 식으로 쉽게 이해할 수 있었습니다.
with() 함수
with() 함수는 인자로 받은 객체를 이어지는 함수 블록의 리시버로 전달합니다.
fun selectedView(view : TextView){
with(view){
setOnClickListener { }
text = "~~~~"
setTextColor(컬러값)
}
}
저는 with를 이해할 때 ~와 함께 즉, 위에서는 인자로 받은 view와 함께 ~ 이런식으로 이해했습니다.
run() 함수
run() 함수는 인자가 없는 익명 함수처럼 사용하는 형태와 객체에서 호출하는 형태를 제공합니다.
이 함수는 복잡한 계산을 위해 여러 임시 변수가 필요할 때 유용하게 사용할 수 있습니다.
var sum = run {
var a = 4
var b = 2
a + b
}
예를 들어 sum이라는 변수값에 특정 변수들의 합을 대입하고 싶은 경우 위와 같이 run() 함수를 통해 sum을
표현할 수 있습니다.
위의 구문에서 run{~~} 중괄호 안의 변수들은 외부에 노출되지 않습니다.
즉, 복잡한 계산인 경우 여러 임시 변수가 필요할 때 유용할 수 있겠죠
이쯤에서 run()함수와 with() 함수의 차이점이 궁금하실 수 있습니다.
저는 이 둘의 차이를 이해할때 with()함수는 사용할 객체를 매개변수를 통해 받습니다. 즉 해당 매개변수가 value? 인 경우
value != null 일 경우 함수의 호출 자체를 막는 방법을 사용할 수 없으므로, 널 값이 아닌 것으로 확인된 객체에 이 함수를
사용할 것입니다.
하지만, run() 함수는 안전한 호출을 사용할 수 있으므로 ( 함수를 인자가 없는 익명 함수처럼 사용하는 경우 ) 널 값일 수
있는 객체의 속성이나 함수에 연속적으로 접근해야 할 때 유용하다는 것을 이해할 수 있습니다.
참고 문헌 : 커니의 코틀린