1

I have a need to take a list of case classes and convert them to a to a single, comma separated string (with no heading or tailing comma).

case class State(name: String)

def toLine(states: State*): String = {
}

so, toLine(State("one"), State("two"), State("three")) should return one,two,three

here is what I thought of. any better way?

def toLine(states: State*): String = {
  states match {
    case s if s.isEmpty => throw new Exception
    case s => s.tail.foldLeft(s.head.name)(_+","+_) 
  }
}

is there a way to guaranty there will be at least one value in the list?

Ehud Kaldor
  • 753
  • 1
  • 7
  • 20

2 Answers2

3

You can use mkString:

def toLine(states: State*): String = states.map(_.name).mkString(",")

if you need to ensure at least one element you can do:

def toLine(state: State, states: State*) = (state +: states).map(_.name).mkString(",")
Lee
  • 142,018
  • 20
  • 234
  • 287
0

Scala's collections provide a function to do just this: states.map(_.name).mkString(",")

If you want to ensure that toLine is always called with at least one value, you can do this:

def toLine(state: State, states: State*): String = {
  states.map(_.name).mkString(",")
}

This will move that check to the type system, rather than doing so at runtime.

Ryan
  • 7,227
  • 5
  • 29
  • 40
  • interestingly, running your code gave me this: scala> def toLine(state: State, states: State*): String = { | states.mkString(",") | } toLine: (state: State, states: State*)String scala> toLine(State("one"), State("two"), State("three")) res0: String = State(two),State(three) – Ehud Kaldor Mar 12 '15 at 18:06
  • Forgot to map the name. – Ryan Mar 12 '15 at 19:52