Skip to content

Instantly share code, notes, and snippets.

@zsolt-donca
Created February 23, 2017 10:49
Show Gist options
  • Save zsolt-donca/01c3294b149ac3e2067b9b51e9259d04 to your computer and use it in GitHub Desktop.
Save zsolt-donca/01c3294b149ac3e2067b9b51e9259d04 to your computer and use it in GitHub Desktop.
Scala solution (as a worksheet) to the string decoding problem: https://leetcode.com/problems/decode-string
def splitWhile[A](it: Seq[A])(pred: A => Boolean): (Seq[A], Seq[A]) = {
(it.takeWhile(pred), it.dropWhile(pred))
}
def splitParenContentsAndRest(s: Seq[Char]): (Seq[Char], Seq[Char]) = {
assert(s.head == '[')
val parenCounts = s.scanLeft(0) {
case (parenCount, '[') => parenCount + 1
case (parenCount, ']') => parenCount - 1
case (parenCount, _) => parenCount
}
val parenEnd = parenCounts.tail.indexOf(0)
val (paren, rest) = s.splitAt(parenEnd + 1)
val unpackedParen = paren.slice(1, paren.length - 1)
(unpackedParen, rest)
}
def decode(s: Seq[Char]): String = {
if (s.isEmpty) {
""
} else {
val (digits, paren) = splitWhile(s)(_.isDigit)
if (digits.nonEmpty) {
val (parenContents, rest) = splitParenContentsAndRest(paren)
val decodedParen = decode(parenContents)
val count = digits.mkString("").toInt
val decodedRepeated = List.fill(count)(decodedParen)
decodedRepeated.mkString("") + decode(rest)
} else {
val (letters, rest) = splitWhile(s)(_.isLetter)
if (letters.nonEmpty) {
letters.mkString("") + decode(rest)
} else {
sys.error("Unexpected format: " + s)
}
}
}
}
decode("3[a]2[bc]")
decode("3[a2[c]]")
decode("2[abc]3[cd]ef")
decode("100[leetcode]")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment