I have the following array of arrays that represents a cycle in a graph that I want to print in the below format.
scala> result.collect
Array[Array[Long]] = Array(Array(0, 1, 4, 0), Array(1, 5, 2, 1), Array(1, 4, 0, 1), Array(2, 3, 5, 2), Array(2, 1, 5, 2), Array(3, 5, 2, 3), Array(4, 0, 1, 4), Array(5, 2, 3, 5), Array(5, 2, 1, 5))
0:0->1->4;
1:1->5->2;1->4->0;
2:2->3->5;2->1->5;
3:3->5->2;
4:4->0->1;
5:5->2->3;5->2->1;
How can I do this? I have tried to do a for loop with if statements like other coding languages but scala's ifs in for loops are for filtering and cannot make use if/else to account for two different criteria.
example python code
for (array,i) in enumerate(range(0,result.length)):
if array[i] == array[i 1]:
//print thing needed
else:
// print other thing
I also tried to do result.groupBy to make it easier to print but doing that ruins the arrays.
Array[(Long, Iterable[Array[Long]])] = Array((4,CompactBuffer([J@3677a08a)), (0,CompactBuffer([J@695fd7e)), (1,CompactBuffer([J@50b0f441, [J@142efc4d)), (3,CompactBuffer([J@1fd66db2)), (5,CompactBuffer([J@36811d3b, [J@61c4f556)), (2,CompactBuffer([J@2eba1b7, [J@2efcf7a5)))
Is there a way to nicely print the output needed in Scala?
CodePudding user response:
This should do it:
result
.groupBy(_.head)
.toArray
.sortBy(_._1)
.map {
case (node, cycles) =>
val paths = cycles.map { cycle =>
cycle
.init // drop last node
.mkString("->")
}
s"$node:${paths.mkString(";")}"
}
.mkString(";\n")
This is the output for the sample input you provided:
0:0->1->4;
1:1->5->2;1->4->0;
2:2->3->5;2->1->5;
3:3->5->2;
4:4->0->1;
5:5->2->3;5->2->1
CodePudding user response:
It can be done without groupBy()
and subsequent sorting. (Scala 2.13.x)
val collect: Array[Array[Long]] = ... //as posted
List.unfold(collect.map(_.init.mkString("","->",";"))){ ss =>
Option.when(ss.nonEmpty){
val (a,b) = ss.partition(_.startsWith(ss(0).take(1)))
(s"${ss(0).take(1)}:${a.mkString}", b)
}
}.foreach(println)