I don't have the time to test this, so I hope you can do that for me. I decided not to use HashMap straight away because type conversion makes things a bit more complicated than they should, but let me know if this is important for you and causes you trouble.
Here's option 1:
def realize(queryResult: ResultSet): Vector[Map[String, Object]] = {
val md = queryResult.getMetaData
val colNames = for (i <- 1 to md.getColumnCount) yield md.getColumnName(i)
val buildMap = () => (for (n <- colNames) yield n -> queryResult.getObject(n)).toMap
Iterator.continually(queryResult.next()).takeWhile(identity).map(_ => buildMap()).toVector
}
I don't like it much because some parts of the code rely on side effects of other parts of the code, so even if it works, it's still ugly.
Here's option 2, which I like more:
def buildMap(queryResult: ResultSet, colNames: Seq[String]): Option[Map[String, Object]] =
if (queryResult.next())
Some(colNames.map(n => n -> queryResult.getObject(n)).toMap)
else
None
def realize(queryResult: ResultSet): Vector[Map[String, Object]] = {
val md = queryResult.getMetaData
val colNames = (1 to md.getColumnCount) map md.getColumnName
Iterator.continually(buildMap(queryResult, colNames)).takeWhile(!_.isEmpty).map(_.get).toVector
}
Nicer, IMHO, you can save some dots over there but I decided to keep them. Maybe something like this:
(Iterator continually (buildMap(queryResult, colNames)) takeWhile (!_.isEmpty) map (_.get)).toVector
Again, I didn't test it, I don't know how to do it without a DB and I don't feel like setting one up now, sorry for that.
Finally, I'm not sure if you realized this, but "realize" is probably not the best name for this method (or for any method, unless you are programming some epistemic system, IMHO).