Skip to main content
updated current solution, changed example to highlight current weakness, added a desired output section
Source Link
David P.
  • 306
  • 2
  • 7
scala> val rows = combineStrings(List("Backpack""Short", "Canteen","This "Glasses",is "Picka Axe",particularly "Cellularlong Phone"String...", "Quick-draw"More", Holster""Small", "Strings"), 35)
rows: List[String] =

Current Output

scala> Listrows.foreach(Backpack, Canteen,println)
Short
This Glasses,is Picka Axe,particularly Cellularlong PhoneString...
More, Quick-drawSmall, Holster)
Strings

Desired Output

scala> rows.foreach(println)
BackpackShort, CanteenMore, GlassesSmall, Pick AxeStrings
CellularThis Phone
Quick-drawis Holstera particularly long String...
private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")
  match {
      case idx if (idx == -1 || scratch.length < maxLen) {=>
        rows += scratch
        scratch = "" 

    } else case idx if (idx > maxLen) {=>
        rows += scratch.substring(0, idx)
        scratch = scratch.substring(idx+1) 

    } else {case idx =>
        val lIdx = scratch.lastIndexOf("|", maxLen)
        rows += scratch.substring(0, lIdx)
        scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}
  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.
scala> val rows = combineStrings(List("Backpack", "Canteen", "Glasses", "Pick Axe", "Cellular Phone", "Quick-draw Holster"), 35)
rows: List[String] = List(Backpack, Canteen, Glasses, Pick Axe, Cellular Phone, Quick-draw Holster)

scala> rows.foreach(println)
Backpack, Canteen, Glasses, Pick Axe
Cellular Phone
Quick-draw Holster
private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")
 
    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}
  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.
scala> val rows = combineStrings(List("Short", "This is a particularly long String...", "More", "Small", "Strings"), 35)

Current Output

scala> rows.foreach(println)
Short
This is a particularly long String...
More, Small, Strings

Desired Output

scala> rows.foreach(println)
Short, More, Small, Strings
This is a particularly long String...
def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    scratch.indexOf("|") match {
      case idx if (idx == -1 || scratch.length < maxLen) =>
        rows += scratch
        scratch = "" 

      case idx if idx > maxLen =>
        rows += scratch.substring(0, idx)
        scratch = scratch.substring(idx+1) 

      case idx =>
        val lIdx = scratch.lastIndexOf("|", maxLen)
        rows += scratch.substring(0, lIdx)
        scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.
added Example Usage to demonstrate input/output of method.
Source Link
David P.
  • 306
  • 2
  • 7

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Example Usage

scala> val rows = combineStrings(List("Backpack", "Canteen", "Glasses", "Pick Axe", "Cellular Phone", "Quick-draw Holster"), 35)
rows: List[String] = List(Backpack, Canteen, Glasses, Pick Axe, Cellular Phone, Quick-draw Holster)

scala> rows.foreach(println)
Backpack, Canteen, Glasses, Pick Axe
Cellular Phone
Quick-draw Holster

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Example Usage

scala> val rows = combineStrings(List("Backpack", "Canteen", "Glasses", "Pick Axe", "Cellular Phone", "Quick-draw Holster"), 35)
rows: List[String] = List(Backpack, Canteen, Glasses, Pick Axe, Cellular Phone, Quick-draw Holster)

scala> rows.foreach(println)
Backpack, Canteen, Glasses, Pick Axe
Cellular Phone
Quick-draw Holster

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

Please do not add "thanks" - show them with upvotes after 15 rep
Source Link
Jamal
  • 34.9k
  • 13
  • 133
  • 237

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

Thanks.

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

Thanks.

I came across an issue the other day where I really just could not think of a functional solution. So I fell back on my imperative programming skills. Since a functional solution still eludes me, I figured I'd shout out for some help here.

Use Case

I have a List of Strings with arbitrary lengths. These Strings need to be combined into rows that have the same max length.

When a single String's length is greater than max length, that String just gets it's own row as each row eventually get's handled by a function that ensures all Strings are truncated to an appropriate length.

Current Solution

private def combineStrings(strs: List[String], maxLen: Int)
: List[String] = {
  import scala.collection.mutable.ListBuffer

  var scratch = strs.mkString("|")
  val rows = ListBuffer[String]()

  while (scratch.length > 1) {
    val idx = scratch.indexOf("|")

    if (idx == -1) {
      rows += scratch
      scratch = ""
    } else if (idx > maxLen) {
      rows += scratch.substring(0, idx)
      scratch = scratch.substring(idx+1)
    } else {
      val lIdx = scratch.lastIndexOf("|", maxLen)
      rows += scratch.substring(0, lIdx)
      scratch = scratch.substring(lIdx+1)
    }
  }

  rows.toList.map(_.replaceAll("\\|", ", "))
}

Notes

  • Looking at it again, I think I'd replace the if statements with a match.
  • Pipes are used because the original Strings are more likely to have their own commas than their own pipes. Maybe other solutions won't need this hackery.
  • Strings are kept in the same order, but in the end I'd prefer to have the most "compact" rows possible.

Summary

Any ideas on how to make this more functional would be greatly appreciated. I found several functions in Scala's "String" that looked promising, but I'm not really sure how to integrate them with the length requirements.

Source Link
David P.
  • 306
  • 2
  • 7
Loading