I'm using ScalaFX and JavaFX, and have this code:
import scalafx.Includes._
class Type1(anInt: Int, ...)
class Type2(aString: String, ...)
class ListItem[T](internalValue:T, ...)
object Worker
{
val list1 = FXCollections.observableArrayList[ListItem[Type1]]()
val list2 = FXCollections.observableArrayList[ListItem[Type2]]()
def workWithList(list:ObservableList[ListItemType]) {
list.foreach(i => workWithItem(i))
}
def workWithItem(item:ListItem) {
item match {
case i:ListItem[Type1] => do something
case i:ListItem[Type2] => do something else
}
}
workWithList(list1)
workWithList(list2)
}
My problem is that this code doesn't compile; it says that I can't use ObservableList[ListItem[Type1]] for the workWithList
method, which expects ObservableList[ListItem].
As I've been playing with this, some variations of this code says that there are unchecked warnings, and that pattern matching won't work due to type erasure.
Ideally:
- there would be just a single list that could hold objects of type ListItem[Type1] and ListItem[Type2]
- I could do pattern matching when working with the items to do different things depending on what kind of item is being worked with
workWithItem
could work with either type of item. In my current code I've had to change the signature toworkWithItem(item:ListItem[_])
and then doworkWithItem(someItem.asInstanceOf[ListItem[_]])
. Probably not the correct thing to do!
Thanks!
The method signature for workWithList looks wrong - where does the
ListItemType
type come from? Should this bedef workWithList(list: ObservableList[ListItem[_]]) { ...
?If so, then the problem you will run up against in the match cases is that due to type erasure, the JVM can't tell the difference at runtime between the type signatures of the cases. This can be worked around by, for example, turning the Type1, Type2 and ListItem into case classes (or manually generating unapply methods for them), then deconstructing the item in the match cases, like so:
Note that I am working here without specific knowledge of the FX libraries (I tried this using straight scala Lists rather than
ObservableList
orFXCollections.observableArrayList
), so they may affect the applicability of this solution (and might be whereListItemType
is defined).The method signature for workWithItem is fine, but the
asInstanceOf
cast you tried shouldn't be required.