2017-06-16 48 views
0

我已經花了,而黑客在此,仍然不能完全得到該型系統與我同意這種抽象是一個真正的如何在Scala貓中構建一個EitherT的Kleisli實例?

ObjectMapper => A => Either[Throwable, B] 

我現在的類型看起來像

import cats._ 
import cats.data.{Reader, Kleisli, EitherT} 
import cats.implicits._ 
import com.fasterxml.jackson.databind.{ObjectMapper, JsonNode} 

type JsonParser[A, B] = Kleisli[EitherT[Reader[A, ?], Throwable, ?], ObjectMapper, B] 

爲了測試實例化這種類型的,我寫了一個很簡單的功能,需要一個JSON String,並返回一個Either[Throwable, JsonNode]

val makeJsonNode: JsonParser[String, JsonNode] = 
    Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 

我收到此錯誤信息:

[info] Compiling 6 Scala sources to .../scala-2.11/classes... 
[error] Test.scala:140: missing parameter type 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error]   ^
[error] Test.scala:140: missing parameter type 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error]         ^
[error] Test.scala:140: no type parameters for method apply: (value: F[Either[A,B]])cats.data.EitherT[F,A,B] in object EitherT exist so that it can be applied to arguments (cats.data.Reader[Any,Nothing]) 
[error] --- because --- 
[error] argument expression's type is not compatible with formal parameter type; 
[error] found : cats.data.Reader[Any,Nothing] 
[error]  (which expands to) cats.data.Kleisli[cats.Id,Any,Nothing] 
[error] required: ?F[Either[?A,?B]] 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error]      ^
[error] Test.scala:140: type mismatch; 
[error] found : cats.data.Reader[Any,Nothing] 
[error]  (which expands to) cats.data.Kleisli[cats.Id,Any,Nothing] 
[error] required: F[Either[A,B]] 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error]         ^
[error] Test.scala:140: no type parameters for method apply: (run: A => F[B])cats.data.Kleisli[F,A,B] in object Kleisli exist so that it can be applied to arguments (<error> => cats.data.EitherT[F,A,B]) 
[error] --- because --- 
[error] argument expression's type is not compatible with formal parameter type; 
[error] found : <error> => cats.data.EitherT[F,A,B] 
[error] required: ?A => ?F[?B] 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error] ^
[error] Test.scala:140: type mismatch; 
[error] found : cats.data.Kleisli[F,A,B] 
[error] required: Test.this.Parser[String,com.fasterxml.jackson.databind.JsonNode] 
[error]  (which expands to) cats.data.Kleisli[[γ$1$]cats.data.EitherT[[β$0$]cats.data.Kleisli[[A]A,String,β$0$],Throwable,γ$1$],com.fasterxml.jackson.databind.ObjectMapper,com.fasterxml.jackson.databind.JsonNode] 
[error]  Kleisli(mapper => EitherT(Reader(json => tryToEither(Try(mapper.readTree(json)))))) 
[error]   ^
[error] 6 errors found 
[error] (compile:compileIncremental) Compilation failed 
[error] Total time: 2 s, completed Jun 16, 2017 1:28:17 PM 

我意識到這類型是有點麻煩,絕對可以提高(以及可能是矯枉過正),但我挖現在爲了更多地瞭解我自己個人成長的Cats和Scala類型系統,斯卡拉試圖告訴我什麼是錯誤的,在這裏,我該如何解決這個問題?

+0

玩了一會之後,我覺得類型刪除可能是罪魁禍首。我是否在這個猜想的正確軌道上? – josiah

回答

0

基礎的問題是缺少的參數類型,嘗試

Kleisli((mapper: ObjectMapper) => EitherT(Reader((json: String) => tryToEither(Try(mapper.readTree(json)))))) 

您只能使用lambda沒有指定參數類型時,有一個預期的類型,給這個信息,在這種情況下makeJsonNode: JsonParser[String, JsonNode]似乎並不夠了。

相關問題