외부 소스에서 역 직렬화되는 몇 가지 규칙을 지정하는 밀폐 된 케이스 클래스 패밀리가 있습니다. 나는 또한 그와 같은 실제 로직을 수행하는 데 몇 인스턴스와 typeclass이 : 이제암시 적 인스턴스가있는 밀폐 케이스 클래스 패밀리와 일치하는 함수를 자동으로 생성하는 방법은 무엇입니까?
import scala.util.Try
sealed trait ReaderConfig
case class Substring(begin: Int, end: Int) extends ReaderConfig
case class Regex(expr: String) extends ReaderConfig
trait Read[M[_], RC <: ReaderConfig] {
def apply(config: RC, raw: String): M[String]
}
object Read {
implicit val TryReadSubstring: Read[Try, Substring] = (config: Substring, raw: String) => Try {
raw.substring(config.begin, config.end)
}
implicit val TryReadRegex: Read[Try, Regex] = (config: Regex, raw: String) => Try {
config.expr.r.findFirstIn(raw).get
}
trait Helper[RC <: ReaderConfig] {
def as[M[_]](implicit read: Read[M, RC]): M[String]
}
def apply[RC <: ReaderConfig](config: RC)(raw: String) = new Helper[RC] {
override def as[M[_]](implicit read: Read[M, RC]): M[String] = read.apply(config,raw)
}
}
, 올바른 암시를 찾을 아무 문제가 없습니다 구체적인 유형을 사용하는 동안. I 입력하는 (예 I가 상기 한 바와 같이 직렬화 될 때와 같은) 상부의 특성을 갖는 브로있을 때
@ val ok: Try[String] = Read(Substring(0,1))("abc").as[Try]
ok: Try[String] = Success("a")
@ val Fail: Try[String] = Read(Substring(1000,9001))("abc").as[Try]
Fail: Try[String] = Failure(
java.lang.StringIndexOutOfBoundsException: String index out of range: 9001
)
, 그것은 예상대로 컴파일 실패
@ val config: ReaderConfig = Substring(0,1)
config: ReaderConfig = Substring(0, 1)
@ val fail2: Try[String] = Read(config)("abc").as[Try]
cmd8.sc:1: could not find implicit value for parameter read: $sess.cmd2.Read[scala.util.Try,$sess.cmd1.ReaderConfig]
val fail2: Try[String] = Read(config)("abc").as[Try]
^
Compilation Failed
유일한 솔루션 I 같은 올바른 인스턴스와 실제 유형을 일치하는 함수를 작성하는 것입니다 내놓았다 :
val tryRead: ReaderConfig => String => Try[String] = {rc => raw => rc match {
case s: Substring => Read[Substring](s)(raw).as[Try]
case r: Regex => Read[Regex](r)(raw).as[Try]
}}
는 그 다음 행복하게 컴파일하고 내가 그 상황에서 사용할 수 있습니다. 컴파일러는 case
의 누락에 대해 나에게 경고해야하므로
@ tryRead(config)("abc")
res9: Try[String] = Success("a")
형질
는 밀봉되어 있지만, 분명히 그것은 최대한 빨리 해당 인스턴스의 이상을 가지고 매우 성가신 것으로 판명됩니다.이 기능을 자동으로 생성 할 수있는 방법이 있습니까? 결국은 case
을 복사하여 붙여 넣고 변수 패턴을 채워서 만들 수있는 것입니다.