LeetCode - The World's Leading Online Programming Learning Platform
I
can be placed before V
(5) and X
(10) to make 4 and 9.X
can be placed before L
(50) and C
(100) to make 40 and 90.C
can be placed before D
(500) and M
(1000) to make 400 and 900.1 <= num <= 3999
로마문자를 숫자로 바꾸는 문제에서 Map을 쓰는 것보다 When 구문을 쓰는 것이 더 빠른 것을 확인하였으므로, When으로 조건 분기를 하여 풀었다. → Sol1
하지만 실행 시간 점수가 그리 좋지 않았다. 단순한 코드여서 딱히 발전시킬 부분을 찾지 못해서, 다른 사람의 코드를 참고하다, 자릿수 처리가 깔끔한 코드를 발견하였다. 위에서 정해진 조건이 작을 경우 Map보다 When이 더 좋다고 언급했는데, 해당 코드에서는 배열 2개를 사용하여 추가적인 메모리를 사용하긴 하지만, 더 간단하고 직관적으로 짜여있었다. → Sol2
When 구문으로 조건 분기
조건이 많지 않으므로 When 구문 사용
import java.lang.StringBuilder
class Solution {
fun intToRoman(num_: Int): String {
val sb = StringBuilder()
var digitCnt = 1
var num = num_
while (num != 0) {
val digit = num % 10 * digitCnt // 각 자릿수만 가져오기
num /= 10
when (digit) {
in 1..3 -> sb.append("I".repeat(digit))
4 -> sb.append("VI")
5 -> sb.append('V')
in 6..8 -> sb.append("I".repeat(digit - 5) + "V")
9 -> sb.append("XI")
in 10..30 -> sb.append("X".repeat(digit / 10))
40 -> sb.append("LX")
50 -> sb.append('L')
in 60..80 -> sb.append("X".repeat(digit / 10 - 5) + "L")
90 -> sb.append("CX")
in 100..300 -> sb.append("C".repeat(digit / 100))
400 -> sb.append("DC")
500 -> sb.append('D')
in 600..800 -> sb.append("C".repeat(digit / 100 - 5) + "D")
900 -> sb.append("MC")
in 1000..3000 -> sb.append("M".repeat(digit / 1000))
}
digitCnt *= 10
}
return sb.reversed().toString()
}
}
시간 복잡도: 문자열 순회 = n → 최악의 경우 4
배열 2개로 문자 변환
각 자릿수 변환을 뺄셈으로 처리
class Solution {
val ints = arrayOf(1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4 ,1)
val romans = arrayOf("M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX","V", "IV", "I")
fun intToRoman(num: Int) : String{
var result = ""
var num = num
for ((index, i) in ints.withIndex()){
while (num >= i){ // 현재 기준 값보다 크다면
// 기준값을 빼주고, 기준값의 로마값을 결과에 추가
num -= i
result += romans[index]
}
}
return result
}
}
시간 복잡도: 배열 순회(ints) X 문자 변환 = 최악의 경우 15 (3888)