Skip to content

Instantly share code, notes, and snippets.

@bigsaigon333
Last active June 6, 2022 05:47
Show Gist options
  • Save bigsaigon333/434c3145c2914bdca9db8e685407ebcb to your computer and use it in GitHub Desktop.
Save bigsaigon333/434c3145c2914bdca9db8e685407ebcb to your computer and use it in GitHub Desktop.
코드스피츠 90회차 1강 과제
import java.util.*
val trim = """[^.\d-+*()/]""".toRegex()
fun trim(v: String): String = v.replace(trim, "")
val MtoPM = """(?<!^|[*/(])-""".toRegex()
fun repMtoPM(v: String): String = v.replace(MtoPM, "+-")
val re = """^(-?[.\d]+|[+/*()])""".toRegex()
fun parse(v: String) = re.find(v)
fun eval(op: String, leftValue: Double, rightValue: Double): Double = when (op) {
"+" -> leftValue + rightValue
"*" -> leftValue * rightValue
"/" -> leftValue / rightValue
else -> throw Throwable("Invalid operator $op")
}
fun calc(v: String): Double {
var str = repMtoPM(trim(v))
val next = {
val (all, value) = parse(str)?.groupValues ?: throw Throwable("Invalid string $str")
str = str.substring(all.length)
value
}
fun f(env: LinkedList<Pair<Double, String>>): Double {
val token = next()
val cur = if (token == "(") {
f(LinkedList<Pair<Double, String>>())
} else {
token.toDouble()
}
val op = try {
next()
} catch (_: Throwable) {
var result = cur
while (!env.isEmpty()) {
val (prev, pop) = env.pop()
result = eval(pop, prev, result)
}
return result
}
if (op == ")") {
var result = cur
while (!env.isEmpty()) {
val (prev, pop) = env.pop()
result = eval(pop, prev, result)
}
return result
}
if (env.isEmpty()) {
env.push(cur to op)
} else {
val (prev, pop) = env.first
when (pop) {
"+" -> {
when (op) {
"*", "/" -> {
env.push(cur to op)
}
"+" -> {
env.pop()
env.push(eval(pop, prev, cur) to op)
}
else -> throw Throwable("Invalid operator $op")
}
}
"*", "/" -> {
when (op) {
"*", "/", "+" -> {
env.pop()
env.push(eval(pop, prev, cur) to op)
}
else -> throw Throwable("Invalid operator $op")
}
}
else -> throw Throwable("Invalid operator $pop")
}
}
return f(env)
}
return f(LinkedList<Pair<Double, String>>())
}
fun main() {
println(calc("-2 * -3 + 0.4 / - 0.2") == 4.0)
println(calc("2 * 3 + 0.4 / 0.2") == 8.0)
println(calc("-2 -3 + 0.4") == -4.6)
println(calc("1 + 2 * 3 / 4 + 7") == 9.5)
println(calc("-1 -2 * -3 / -4 -7") == -9.5)
println(calc("1 * 2 + 3 / 4 + 7") == 9.75)
println(calc("-1 * -2 -3 / -4 -7") == -4.25)
println(calc("-1 * 2 + 3 / -4 * 7") == -7.25)
println(calc("-1 * -2 -3 / -4 * -7") == -3.25)
println(calc("-2 *(-3 + 0.4)/ -0.2") /* == -26.0 */)
println(calc("-2 +(-3 * 0.4)/ -0.2") /* == 4.0 */)
println(calc("-2 +(-3 * (-5 + 0.4) )/ -0.2") /* == -71.0 */)
println(calc("-2 +((-3 +9) * (-5 + 0.4) )/ -0.2") /* == 136 */)
println(calc("-2 +(-3 + 0.4 * 2) * 5") /* == -13 */)
println(calc("3 +(4 + 5 * 6 + 7) * 7") /* == 290 */)
println(calc("(1 + 2 ) * 3 + 4 * (5 + 6)") /* == 53 */)
println(calc("1 + ( 2 + (3 + (4 + ( 5 + (6 + 7)))))") /* == 28 */)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment