Implicits and evidence

100 views
Skip to first unread message

Edmondo Porcu

unread,
May 11, 2012, 7:21:31 AM5/11/12
to scala-user
Dear members,
I am confused by the chapter 21.8 of Cay S. Horstmann book "Scala for
the Impatience" where the author writes about evidence.

I am confused about the usefulness of T=:=U , T<:<U and T<%<U . I
would be thankful if you could provide practical examples!

Best
Edmondo

Miles Sabin

unread,
May 11, 2012, 7:33:33 AM5/11/12
to Edmondo Porcu, scala-user
Take a look at max, min, sum and product on Seq (well,
GenTraversableOnce actually).

Cheers,


Miles

--
Miles Sabin
tel: +44 7813 944 528
gtalk: mi...@milessabin.com
skype: milessabin
g+: http://www.milessabin.com
http://twitter.com/milessabin
http://underscoreconsulting.com
http://www.chuusai.com

missingfaktor

unread,
May 11, 2012, 8:12:55 AM5/11/12
to Edmondo Porcu, scala-user
You must have noticed that when you call `.toMap` on a list, it gives you a map:

scala> List((1, 9), (2, 3), (5, 89)).toMap
res1: scala.collection.immutable.Map[Int,Int] = Map(1 -> 9, 2 -> 3, 5 -> 89)

...but only when the list is of 2-tuples. 

For other types of list, it raises a type error.

scala> List("hello", "world").toMap
<console>:8: error: Cannot prove that java.lang.String <:< (T, U).
              List("hello", "world").toMap
                                     ^

This is achieved using an implicit evidence parameter A <:< (T, U) where A is the element type in list. 

There are several such methods in standard library that make use of evidence parameters.

On Fri, May 11, 2012 at 4:51 PM, Edmondo Porcu <edmond...@gmail.com> wrote:
Dear members,
I am confused by the chapter 21.8 of Cay S. Horstmann book "Scala for
the Impatience" where the author writes about evidence.

I am confused about the usefulness of T=:=U , T<:<U and T<%<U . I

T <%< U has been deprecated. Use T => U instead.
 
would be thankful if you could provide practical examples!

Best
Edmondo



--
Cheers,

Edmondo Porcu

unread,
May 11, 2012, 8:17:16 AM5/11/12
to missingfaktor, scala-user
I am still missing few points...

1) why do you have three type of evidences? T=:=U and T<:<U , U=>T ?
2) What is the difference between U=>T and the other two ?

Thank you

Edmondo
2012/5/11 missingfaktor <rahul.ph...@gmail.com>:

missingfaktor

unread,
May 11, 2012, 8:23:19 AM5/11/12
to Edmondo Porcu, scala-user
Implicit evidence of type T =:= U tells you that types T and U are the same.

Implicit evidence of type T <:< U tells you that T is a subtype of U.

Implicit evidence of type U => T tells you that there exists an implicit conversion from U to T.
--
Cheers,

missingfaktor

unread,
May 11, 2012, 8:48:51 AM5/11/12
to Edmondo Porcu, scala-user


On Fri, May 11, 2012 at 6:03 PM, Edmondo Porcu <edmond...@gmail.com> wrote:
I understand,

1) but if two types are the same, they are the same type, so why would
you need them to be constrained?

Assume you have a class Foo with type parameter A. It contains a bunch of methods, some of which are applicable to only some values of A. That's where evidence parameters come in. You use them to specify those additional constraints under which the method would be applicable.

A contrived example of =:= :

scala> case class Foo[A](a: A) {
     |   def +(that: Foo[Int])(implicit ev: A =:= Int) = Foo(this.a + that.a)
     |   override def toString = a.toString
     | }
defined class Foo

scala> val a, b = Foo(5)
a: Foo[Int] = 5
b: Foo[Int] = 5

scala> a + b
res0: Foo[Int] = 10

scala> Foo("hello") + Foo("world")
<console>:10: error: type mismatch;
 found   : java.lang.String("world")
 required: Int
              Foo("hello") + Foo("world")
                                 ^

scala> Foo("hello") + Foo(11)
<console>:10: error: Cannot prove that java.lang.String =:= Int.
              Foo("hello") + Foo(11)
                           ^

scala> Foo(3).toString
res3: java.lang.String = 3

scala> Foo("hello").toString
res4: java.lang.String = hello
 

2) If T<:<:U why don't one writes myMethod[U,T<:U] and uses the evidence?


Because the type parameter to be constrained is on class. The constraint however has to be limited to a method.

class List[+A] {
  /* stuff */
  def toMap[T, U](implicit ev: A <:< (T, U)): Map[T, U] = /* stuff */
  /* stuff */
}

Other methods on list do not require that A be a 2-tuple2. So it would be wrong to have that constraint at class level.  


3) I can clearly see the usefulness

Best
Edmondo



2012/5/11 missingfaktor <rahul.ph...@gmail.com>:



--
Cheers,

Dominik

unread,
May 11, 2012, 9:00:00 AM5/11/12
to scala...@googlegroups.com, Edmondo Porcu

Take a look at max, min, sum and product on Seq (well,
GenTraversableOnce actually).

I see no evidence parameters when I look at the definition of these methods: 

abstract def max[A1 >: A](implicit ord: Ordering[A1]): A

abstract def min[A1 >: A](implicit ord: Ordering[A1]): A

abstract def product[A1 >: A](implicit num: Numeric[A1]): A1

abstract def sum[A1 >: A](implicit num: Numeric[A1]): A1

did I miss something?


Dominik

Edmondo Porcu

unread,
May 11, 2012, 9:31:47 AM5/11/12
to missingfaktor, scala-user
Thank you....
That was the factor I was missing!

It let you implement specialized methods which you will be able to
call only for specific type constraint :D

Too good to be true :) Does it come with any performance warning or
can be used without moderation ?:)

Best


2012/5/11 missingfaktor <rahul.ph...@gmail.com>:

missingfaktor

unread,
May 11, 2012, 9:58:50 AM5/11/12
to Edmondo Porcu, scala-user
On Fri, May 11, 2012 at 7:01 PM, Edmondo Porcu <edmond...@gmail.com> wrote:
Thank you....
That was the factor I was missing!

It let you implement specialized methods which you will be able to
call only for specific type constraint :D

Too good to be true :) Does it come with any performance warning or
can be used without moderation ?:)

=:= and <:< have one object pre-allocated each. So performance will be same as that of passing an extra object as a parameter. https://github.com/scala/scala/blob/v2.9.2/src/library/scala/Predef.scala#L413



--
Cheers,

Reply all
Reply to author
Forward
0 new messages