object Demo extends App {
def cartesian[T](x: List[List[T]]): List[List[T]] = {
def partialCartesian(x: List[T], y: List[List[T]]): List[List[T]] =
for {
head <- x
tail <- y
} yield head +: tail
x match {
case head :: Nil => head.map(List(_))
case head :: tail => partialCartesian(head, cartesian(tail))
}
}
val a = List(List(1, 2, 3), List(4, 5), List(6, 7, 8, 9))
cartesian(a).foreach(println)
}
>> List(1, 4, 6)
>> List(1, 4, 7)
>> List(1, 4, 8)
>> List(1, 4, 9)
>> List(1, 5, 6)
>> List(1, 5, 7)
>> List(1, 5, 8)
>> List(1, 5, 9)
>> List(2, 4, 6)
>> List(2, 4, 7)
>> List(2, 4, 8)
>> List(2, 4, 9)
>> List(2, 5, 6)
>> List(2, 5, 7)
>> List(2, 5, 8)
>> List(2, 5, 9)
>> List(3, 4, 6)
>> List(3, 4, 7)
>> List(3, 4, 8)
>> List(3, 4, 9)
>> List(3, 5, 6)
>> List(3, 5, 7)
>> List(3, 5, 8)
>> List(3, 5, 9)
I use 'List' not 'Set' - for shortest code.
P.S. Sorry for my english.