암시적 변환
암시적 변환 (Implicit Conversions)
암시적 변환은 컴파일러가 몇 가지 상황에서 자동으로 적용하는 변환을 말해요. 흔히 뷰(view)라고도 불러요.
본문
컴파일러가 암시적 변환을 적용하는 상황은 두 가지예요.
T타입의 식e를 만났는데, 컴파일러가S타입의 식을 필요로 하는 경우e.m형태의 식을 만났는데,e의 타입이T이고T에는 멤버m이 정의되어 있지 않은 경우
이런 경우 컴파일러는 암시적 스코프에서 T 타입의 식을 S 타입의 식으로 바꿔 줄 수 있는 변환(두 번째 경우라면 m 멤버를 정의한 타입으로 바꿔 줄 수 있는 변환)을 찾아요.
이 변환은 다음 두 가지 중 하나가 될 수 있어요.
T => S또는(=> T) => S타입의 암시적def(implicit def)scala.Conversion[T, S]타입의 암시적 값(implicit value)
암시적 변환을 정의하면, 스코프 안에 import scala.language.implicitConversions가 있거나 컴파일러에 -language:implicitConversions 플래그를 준 게 아니라면 경고가 발생해요.
예시
첫 번째 예시는 scala.Predef에서 가져온 거예요. 이 암시적 변환 덕분에 java.lang.Integer를 기대하는 Java 메서드에 scala.Int를 넘겨줄 수 있어요.
import scala.language.implicitConversions
implicit def int2Integer(x: Int): java.lang.Integer =
x.asInstanceOf[java.lang.Integer]
두 번째 예시는 Conversion을 활용해서, 다른 타입들의 Ordering이 이미 있을 때 임의의 타입에 대한 Ordering을 정의하는 방법을 보여줘요.
import scala.language.implicitConversions
implicit def ordT[T, S](
implicit conv: Conversion[T, S],
ordS: Ordering[S]
): Ordering[T] =
// `ordS` compares values of type `S`, but we can convert from `T` to `S`
(x: T, y: T) => ordS.compare(x, y)
class A(val x: Int) // The type for which we want an `Ordering`
// Convert `A` to a type for which an `Ordering` is available:
implicit val AToInt: Conversion[A, Int] = _.x
implicitly[Ordering[Int]] // Ok, exists in the standard library
implicitly[Ordering[A]] // Ok, will use the implicit conversion from
// `A` to `Int` and the `Ordering` for `Int`.
이 예시에서 ordT는 Conversion[T, S]와 Ordering[S]를 받아 Ordering[T]를 만들어 내요. S 타입의 값들을 비교해 주는 ordS가 있고 T에서 S로 변환할 수 있으니, A에 대한 Ordering을 굳이 A를 위한 비교 로직 없이도 얻을 수 있죠. implicitly[Ordering[A]]가 동작하는 이유가 바로 이 암시적 변환 덕분이에요. 이에 대한 더 자세한 내용은 관련 문서를 참고해 주세요.