so

Generics in Scala

Volume 3, Issue 13; 04 Apr 2019

The intersection of Java generics and Scala is…not going well for me.

I freely admit to being a little out of my depth here. My formal training in type systems is a good few decades behind me. I’ve used generics in Java rather trivially once or twice, but they’re not something about which I can claim to have a deep and thorough understanding. I’m also a relative newcomer to Scala, so I’m not claiming a deep or thorough understanding of its type system either.

I set out this evening to update my XML Calabash v2 implementation, written in Scala (2.12 today) to use Saxon 9.9. Saxon 9.9 introduces generics in a number of places. Fine by me. I can cope, I imagine.

Except, I can’t apparently.

The stumbling block is trying to implement a class that extends the ExtensionFunctionDefinition class.Saxonica don’t appear to publish versioned APIs, so if you’re reading this much after 3 April 2019, take what you find at those pages with a grain of salt. It has an inner class that extends the ExtensionFunctionCall class. That, in turn, has an abstract method, call, defined thusly in Java:

public abstract Sequence<?> call(
    XPathContext context,
    Sequence[] arguments
)

My first attempt to define this in Scala was:

override def call(
    context: XPathContext,
    arguments: Array[Sequence]
): Sequence[_]

but that doesn’t compile: “trait Sequence takes type parameters”. For my second attempt, I tried:

override def call(
    context: XPathContext,
    arguments: Array[Sequence[_]]
): Sequence[_]

But that, I’m told, doesn’t override anything. Hark, the compiler says: [error] (Note that Array[net.sf.saxon.om.Sequence] does not match Array[net.sf.saxon.om.Sequence[_]]: their type parameters differ)

And here we seem to be at an impasse. I can just implement the damned thing in Java, of course, but is this an actual limitation in Scala or in my understanding?

I was lying before, by the way, about my first attempt. My first attempt was actually:

override def call(
    context: XPathContext,
    arguments: Array[Sequence[_ <: Item[_ <: Item[_]]]]
): Sequence[_ <: Item[_ <: Item[_]]]

which I crafted by bluntly copying Java into Scala and letting IntelliJ IDEA translate it. I had failed to work out what to do with the recursive nature of the Item declaration.

Update 4 Apr 2019: When the answer failed to turn up on Twitter in a timely fashion, I decided to ask stackoverflow which is probably what I should have done in the first place.

Update 13 Apr 2019: In the end, I punted and wrote Java shims that call Scala implementations. It may not be pretty, but it works.

Please provide your name and email address. Your email address will not be displayed and I won’t spam you, I promise. Your name and a link to your web address, if you provide one, will be displayed.

Your name:

Your email:

Homepage:

Do you comprehend the words on this page? (Please demonstrate that you aren't a mindless, screen-scraping robot.)

What is nine minus three?  (e.g. six plus two is 8)

Enter your comment in the box below. You may style your comment with the CommonMark flavor of Markdown.

All comments are moderated. I don’t promise to preserve all of your formatting and I reserve the right to remove comments for any reason.