简体   繁体   English

从绑定到集合类型参数的上下文隐式

[英]implicit from context bound on collection type parameter

I have some code that streams a response by converting a Stream of case classes to json representations using spray.json. 我有一些代码通过使用spray.json将案例类的Stream转换为json表示来流式传输响应。 This works fine for a single case class, but I want to genericize it. 这对于单个案例类来说效果很好,但我想对其进行泛化。

So I'm starting with case classes like this: 所以我从这样的案例类开始:

import spray.json._
import spray.json.DefaultJsonProtocol._
case class Item(foo: String, bar: Int)
case class Report(baz: String, stream: Stream[Item])
object Protocol { implicit val ItemFormat = jsonFormat2(Item) }

In my report streaming method I have code like this (highly simplified): 在我的报告流式传输方法中,我有如下代码(高度简化):

def streamReport(...) {
    import Protocol._

    val handler: PartialFunction[Try[Any], String] = {
        case Success(Report(_, stream)) =>
            stream.head.toJson.compactPrint
    }
}

What I'd like to do is genericize Report to support more than Item: 我想做的是将Report泛化为不仅支持Item:

case class Report[T](baz: String, stream: Stream[T])

But now, of course, the streamReport method can't find a JsonWriter in scope for type Any . 但是,现在,当然, streamReport方法在类型Any范围内找不到JsonWriter

I can do something close to what I want if I add a type parameter with context bound to streamReport , and pass in the Report directly: 如果我添加一个上下文绑定到streamReport的类型参数,然后直接传递Report ,我可以做些接近我想要的事情:

def jsonStream[T : JsonWriter](report: Report[T]): String = 
    implicitly[JsonWriter[T]].write(report.stream.head).compactPrint

However, I cannot figure out how to get this to work with the PartialFunction . 但是,我不知道如何PartialFunctionPartialFunction The following does not compile (and wouldn't fit exactly anyway as the signature of the partial function is different than above): 以下代码无法编译(由于部分函数的签名与上面的签名不同,因此也无法完全匹配):

def handler[T : JsonWriter](): PartialFunction[T, String] = {
    case Success(Report(_, stream)) =>
        implicitly[JsonWriter[T]].write(report.stream.head).compactPrint
}

I'm not sure where it's going wrong. 我不确定哪里出了问题。 Does it have to do with type erasure, or a problem with having Try[Any] as the parameter type on my partial function? 它与类型擦除有关,还是在我的部分函数中将Try[Any]作为参数类型有问题? How can I get the implicit JsonWriter I need for the element type of the stream? 如何获取流的元素类型所需的隐式JsonWriter?

My guess is that Any is not the problem, the problem is trying to match case Success(Report(_, stream)) , after the definition for Report is now Report[T] . 我的猜测是, Any并不是问题,问题是试图将case Success(Report(_, stream))匹配,之后Report的定义现在为Report[T]

Also, in order to find the right implicit conversion, the compiler needs to understand the type involved (in compile time). 另外,为了找到正确的隐式转换,编译器需要了解所涉及的类型(在编译时)。 Try using something like this: 尝试使用如下所示的内容:

def streamReport[T](...) {
    import Protocol._

    val handler: PartialFunction[Try[Any], String] = {
        case Success(Report[T](_, stream)) =>
            stream.head.toJson.compactPrint
    }
}

That way, the compiler will know what is being matched, and can infer the right type. 这样,编译器将知道要匹配的内容,并可以推断出正确的类型。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM