3

I'm trying to define a generic add function to numeric values:

def add[A](x:A, y:A): A = {
  x + y
}


console:16: error: type mismatch; found : A required: String x + y ^

What's the compiler complaining about? Some of the stuff I've googled does not quite make sense to me at this moment.

user1206899
  • 1,564
  • 1
  • 11
  • 15
  • You have explicitly told the compiler that you have a method that takes two arguments with types that you know nothing about (except that they are the same type). Since you explicitly said to the compiler that you know nothing about the types, you also cannot know that they have a `+` method. – Jörg W Mittag Dec 20 '16 at 11:26
  • 1
    Possible duplicate of [Type parameter in scala](http://stackoverflow.com/questions/39283549/type-parameter-in-scala) – Jörg W Mittag Dec 20 '16 at 12:16

2 Answers2

10

Since you define A with no boundaries and no extra information, it could be any type, and not any Scala type has a + method - so this can't compile.

The error message is a result of the compiler's attempt to implicitly convert x into a String (because String has a + method, and every type can be converted to string using toString), but then it fails because y isn't a string.

To create a method for all numeric types, you can use the Numeric type:

def add[A](x:A, y:A)(implicit n: Numeric[A]): A = {
  n.plus(x, y)
}

add(1, 3)
add(1.4, 3.5)

EDIT: or an equivalent syntax:

def add[A: Numeric](x:A, y:A): A = {
  implicitly[Numeric[A]].plus(x, y)
}
Tzach Zohar
  • 37,442
  • 3
  • 79
  • 85
  • Can't the compiler decide until instantiation or I'm just talking about nonsense here in scala realm. So I believe forgetting about whatever other PL deals with generic programming is what you are suggesting. – user1206899 Dec 19 '16 at 08:17
  • 1
    By definition, compiler runs in compile-time (before running the program), which means instantiation is out of the picture (it only happens in runtime). In Scala, like in any other strongly-typed language, the compiler verifies the correctness of types and their methods, so that you don't get these errors in runtime. – Tzach Zohar Dec 19 '16 at 08:27
2

To be able to do something like this the compiler needs to know that A has a method

def +(a: A): A

so ideally you would want to do something like

def add[A :< Numeric](x:A, y:A): A = { ... 

but you can't because the numeric types in Scala have no common super type (they extend AnyVal). Look here for a related question.

Community
  • 1
  • 1
Simon
  • 6,293
  • 2
  • 28
  • 34