返回

巧妙轻松地将罗马数字转换为整数!

前端

前言:面试题中常见的罗马数字陷阱

相信很多小伙伴在学习算法的过程中都遇到过这样一道面试题:将罗马数字转换为整数。乍一看,这道题似乎很简单,不就是将罗马数字中的字符一一转换为对应的数字,然后将这些数字相加吗?然而,隐藏在其中的一些陷阱很容易让人犯错。

技巧:如何巧妙地应对罗马数字转换

方法一:循环判断

思路与流程

  1. 将罗马数字从左到右依次遍历。
  2. 如果当前字符的值大于或等于下一个字符的值,则将当前字符的值累加到结果中。
  3. 如果当前字符的值小于下一个字符的值,则将当前字符的值减去下一个字符的值,并将结果累加到结果中。
  4. 重复步骤 2 和步骤 3,直到遍历完整个罗马数字字符串。
def roman_to_int(roman_number):
  result = 0
  last_value = 0

  roman_dict = {
      'I': 1,
      'V': 5,
      'X': 10,
      'L': 50,
      'C': 100,
      'D': 500,
      'M': 1000
  }

  for char in roman_number:
    current_value = roman_dict[char]

    if current_value > last_value:
      result = result - last_value + (current_value - last_value)
    else:
      result += current_value

    last_value = current_value

  return result


print(roman_to_int('MCMXCIV'))  # 输出:1994
print(roman_to_int('LVIII'))  # 输出:58
print(roman_to_int('XCIX'))  # 输出:99

方法二:正则表达式

思路与流程

  1. 使用正则表达式匹配罗马数字中可能的字符组合。
  2. 根据匹配到的字符组合,将对应的数字值累加到结果中。
import re

def roman_to_int(roman_number):
  roman_regex = r'(?=[MDCLXVI])M{0,3}(C[DM])|C[MD]{0,3}(X[LC])|X[CM]{0,3}(I[XV])|I[XL]{0,3}'

  result = 0
  last_value = 0

  for match in re.finditer(roman_regex, roman_number):
    current_value = match.group()

    if current_value[0] == 'M':
      result += 1000 * len(current_value)
    elif current_value[0] == 'D':
      result += 500
    elif current_value[0] == 'C':
      result += 100 * len(current_value)
    elif current_value[0] == 'L':
      result += 50
    elif current_value[0] == 'X':
      result += 10 * len(current_value)
    elif current_value[0] == 'V':
      result += 5
    elif current_value[0] == 'I':
      result += len(current_value)

  return result


print(roman_to_int('MCMXCIV'))  # 输出:1994
print(roman_to_int('LVIII'))  # 输出:58
print(roman_to_int('XCIX'))  # 输出:99

结语:

罗马数字的转换并不是一个复杂的概念,但是它需要仔细的观察和思考,以避免陷入常见的陷阱。了解并掌握多种转换方法能够帮助你更加自信地应对算法面试中的罗马数字转换问题。