Home > front end >  Functional way to build a matrix from the list in scala
Functional way to build a matrix from the list in scala

Time:02-16

I've asked this question on https://users.scala-lang.org/ but haven't got a concrete answer yet. I am given a vector v and I would like to construct a matrix m based on this vector according to the rules specified below. I would like to write the following code in a purely functional way, i.e. m = v.map(...) or similar. I can do it easily in procedural way like this

import scala.util.Random

val v =  Vector.fill(50)(Random.nextInt(100))
println(v)

val m = Array.fill[Int](10, 10)(0)

def populateMatrix(x: Int): Unit = m(x/10)(x)  = 1

v.map(x => populateMatrix(x))

m foreach { row => row foreach print; println }

In words, I am iterating through v, getting a pair of indices (i,j) from each v(k) and updating the matrix m at these positions, i.e., m(i)(j) = 1. But I am seeking a functional way. It is clear for me how to implement this in, e.g. Mathematica

v=RandomInteger[{99}, 300]
m=SparseArray[{Rule[{Quotient[#, 10]   1, Mod[#, 10]   1}, 1]}, {10, 10}] & /@ v // Total // Normal

But how to do it in scala, which is functional language, too?

CodePudding user response:

Your populate matrix approach can be "reversed" - map vector into index tuples, group them, count size of each group and turn it into map (index tuple -> size) which will be used to populate corresponding index in array with Array.tabulate:

val v =  Vector.fill(50)(Random.nextInt(100))
val values = v.map(i => (i/10, i))
  .groupBy(identity)
  .view
  .mapValues(_.size)
val result = Array.tabulate(10,10)( (i, j)=> values.getOrElse((i,j), 0))
  • Related