0

I have a function like this:

case class SomeCaseClass(i: Int)

def func[T: Manifest](someArg: Int)(implicit i: String) = {
  SomeCaseClass(2)
}

I need to call func and supply i explicitly

but when I call func[SomeCaseClass](2)("hello"), I get:

error: not enough arguments for method func: (implicit evidence$1: Manifest[ScalaFiddle.this.SomeCaseClass], implicit i: String)ScalaFiddle.this.SomeCaseClass. Unspecified value parameter i. funcSomeCaseClass("hello")

Any way to do it without changing the function's signature?

Barak BN
  • 442
  • 6
  • 14
  • Do you have the real signature (assuming this is a simplified example)? What is the manifest being used for? – Thilo Nov 22 '18 at 12:06
  • In the actual case, the function calls `jValue.extract[T]` of `org.json4s.ExtractableJsonAstNode`. This function's signature is `def extract[A](implicit formats: Formats, mf: scala.reflect.Manifest[A]): A`. In any case, this is part of out infrastructure code, and I am very reluctant to change it. – Barak BN Nov 22 '18 at 12:12
  • 1
    As a side note, having an implicit `string` is not a great idea... although I realize you may have simplified the type for the question. – Lasf Nov 22 '18 at 13:28

2 Answers2

3

You need to give all implicit parameters explicitly if you give any, and T: Manifest means there is an additional implicit parameter.

Happily, implicitly method will summon the implicit which the compiler would have supplied:

func[SomeCaseClass](2)(implicitly, "hello") // inferred to implicitly[Manifest[SomeCaseClass]]
Alexey Romanov
  • 167,066
  • 35
  • 309
  • 487
  • should i need to import anything here ? i'm getting compiler error and my scala version is 2.11 – Balaji Reddy Nov 22 '18 at 12:29
  • No, you shouldn't, it's in `Predef`. Do you get an error with `implicitly[Manifest[SomeCaseClass]]`? If yes, what is the error? – Alexey Romanov Nov 22 '18 at 12:34
  • Type mismatch, expected: Manifest[SomeCaseClass], actual: CanBuildFrom[String, Char, String] – Balaji Reddy Nov 22 '18 at 12:36
  • 1
    There's no `CanBuildFrom` involved in your example code. Obviously if you have different types there you'll need to adjust. You can see it working at https://scalafiddle.io/sf/EYro2yQ/0. – Alexey Romanov Nov 22 '18 at 12:38
  • i'm not really sure why i'm getting this error. but this is not stopping me from running the code and getting the result... – Balaji Reddy Nov 22 '18 at 12:49
0

When I define the method func in my scala REPL, I am finding the output as:

func: [T](someArg: Int)(implicit evidence$1: Manifest[T], implicit i: String)SomeCaseClass

In other words, the same code can also be written as:

def func1[T](someArg: Int)(implicit manifest: Manifest[T], i: String) = {
  SomeCaseClass(2)
}

It is described here as well.

So in the above code, we can see that the implicit section now have two parameters, not the only String. And you need to provide all the params of the implicit section in case you want to fill them explicitly. If you're providing just one it will throw a compilation error.

Hence your method func can be called through the below code:

func(2)(Manifest.classType(classOf[SomeCaseClass]), "hello")
anuj saxena
  • 279
  • 1
  • 7