2

This question is about working with generic types and setting the bound, so please do not freak out because of the library I use. Treat it as an example.

I work with Scalala and use such types DenseMatrix[V], DenseVectorCol[V] and DenseVectorRow[V]. The common super type for them is Tensor[K,V]. Note that the Tensor has additional parameter K -- all the mentioned classes Dense... set this type K by themselves.

So I would like to write a method with argument which upper type bound is Tensor. I wrote such code for my method:

def validate[K,T <: Tensor[K,Double]](tensor : T) : T = ...

with such intention -- T has to be subtype of Tensor, and I know I work with Doubles all the time, so let it be Double, and for first type argument (K) get it from passed argument.

It does not work as I expected because I get error:

inferred type arguments [Nothing,DenseVectorCol[Double]] do not conform to method validate's type parameter bounds [K,T <: Tensor[K,Double]]

QUESTION: so how to extract this type K from the passed argument?

greenoldman
  • 16,895
  • 26
  • 119
  • 185
  • Note that `Tensor` gives you access to its type parameter `K` through its type member `Domain`, which might make it a little easier to get by with `def validate[T <: X[_, Double]] ...` (which will be inferred correctly). – Travis Brown Sep 15 '12 at 19:20
  • @TravisBrown, bingo -- wildcard `_` does the job (I put `Tensor` instead of `X` of course). Why didn't you post a regular answer? Please do. – greenoldman Sep 15 '12 at 19:43

1 Answers1

2

If you don't care about K at all, you can use a wildcard:

def validate[T <: Tensor[_, Double]]: T = ...

Note that in some cases this wouldn't work (e.g., if you needed to return a K or otherwise use it in the method), but assuming this isn't one of those cases, this is a perfectly valid solution and the type inference will work out just fine.

Travis Brown
  • 138,631
  • 12
  • 375
  • 680