#13. Roman to Integer

本文介绍了一种将罗马数字转换为整数的方法。通过解析罗马数字的构成规则,利用递归算法实现转换,并通过详尽的测试确保正确性。

题目描述如下:

Given a roman numeral, convert it to an integer.

Input is guaranteed to be within the range from 1 to 3999.

首先理解题意,搞搞清楚罗马数字的规则。
罗马数字共有7个,
即I(1)、V(5)、X(10)、L(50)、C(100)、D(500)和M(1000)
规则是 左减右加,例如 XVIII = 18, XXIV=24,IX=9
知道了这些就可以做这道题了。
首先最重要的是准备好测试,覆盖面比较全的测试数据是必要的,没有测试数据,没办法对问题产生直观的印象,只是凭借想象是不行的

这个题宏观上讲要用到递归,基于左加右减的原则,我们首先找到的是字符串中代表数字最大的值然后以它为标杆分成左右两个字符串,再分别两个字符串递归地调用该方法。
其他的地方没什么特别难的,但是细节的地方不少,这个时候合适的日志输出就显得非常重要了,本题中我加入了大量数据输出,提高找错误的效率。

具体代码如下:

class Solution {
public:
    int romanToInt(string s) {
        int flag[s.length()];
        int result=0,start=0,end,maxValue=0;
        string tableStr("IVXLCDM");
        int tableNum[7]={1,5,10,50,100,500,1000};

        for(int i=0;i<s.length();i++){
            int ret = tableStr.find(s[i],0);
            flag[i] = ret;
            if(ret>maxValue){
                start = i;
                maxValue = ret;
            }
            //cout<<"ret = "<<ret<<" "<<"start == "<<start<<endl;
        }
        //cout<<"start = "<<start<<endl;
        //end = start+1;
        //这里要特别注意一下 上面的写法会导致运行时越界错误 
        //所有的这种类似指针的操作都要限制范围
        //很多错误编译器是不会检查的,写bug很容易的
        end=start;
        while(end<s.length()&&flag[start]==flag[end])
            end++;
        //cout<<"end = "<<end<<endl;

        result = (end-start)*tableNum[flag[start]];
        //cout<<"result = "<<result<<endl;

        string a(s,end),b(s,0,start);
        //cout<<"Right = "<<a<<endl;
        //cout<<"Left = "<<b<<endl;

        if(a.length()!=0)
            result += romanToInt(a);
        if(b.length()!=0)
            result -= romanToInt(b);
        return result;
    }
};

这个题思路还是很简洁的,不会太过复杂,一开始写的时候并没有注意到测试数据中的递归现象,单纯的用左减右加原则,一下子就错了。
算法的复杂度由于输入数据的限制不予考虑,能够解决问题就好。

Java是一种具备卓越性能与广泛平台适应性的高级程序设计语言,最初由Sun Microsystems(现属Oracle公司)的James Gosling及其团队于1995年正式发布。该语言在设计上追求简洁性、稳定性、可移植性以及并发处理能力,同时具备动态执行特性。其核心特征与显著优点可归纳如下: **平台无关性**:遵循“一次编写,随处运行”的理念,Java编写的程序能够在多种操作系统与硬件环境中执行,无需针对不同平台进行修改。这一特性主要依赖于Java虚拟机(JVM)的实现,JVM作为程序与底层系统之间的中间层,负责解释并执行编译后的字节码。 **面向对象范式**:Java全面贯彻面向对象的设计原则,提供对封装、继承、多态等机制的完整支持。这种设计方式有助于构建结构清晰、模块独立的代码,提升软件的可维护性与扩展性。 **并发编程支持**:语言层面集成了多线程处理能力,允许开发者构建能够同时执行多项任务的应用程序。这一特性尤其适用于需要高并发处理的场景,例如服务器端软件、网络服务及大规模分布式系统。 **自动内存管理**:通过内置的垃圾回收机制,Java运行时环境能够自动识别并释放不再使用的对象所占用的内存空间。这不仅降低了开发者在内存管理方面的工作负担,也有效减少了因手动管理内存可能引发的内存泄漏问题。 资源来源于网络分享,仅用于学习交流使用,请勿用于商业,如有侵权请联系我删除!
### Convert an Integer to a Roman Numeral with Subtractive Rules To convert an integer to a Roman numeral, especially accounting for subtractive combinations like IV (4), IX (9), XL (40), and so on, you can follow a structured approach using predefined mappings of integers to Roman numerals. This method ensures that the subtractive notation is applied correctly. The core idea is to use two arrays: one for the integer values and another for their corresponding Roman numeral representations. These arrays are ordered from the largest to the smallest values, including the special subtractive cases. The algorithm iterates through these values, subtracting them from the input number while appending the corresponding Roman numeral symbols to the result string. Here’s how this can be implemented in Python: ```python def int_to_roman(num): # Define the mapping of integers to Roman numerals, including subtractive cases val = [1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1] syms = ["M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I"] roman_numeral = "" i = 0 while num > 0: while num >= val[i]: roman_numeral += syms[i] num -= val[i] i += 1 return roman_numeral ``` This function works by repeatedly subtracting the largest possible value from the given number and appending the corresponding Roman numeral symbol(s) to the result string. For example, when converting the number 1994, the function first subtracts 1000 (M), then 900 (CM), followed by 90 (XC), and finally 4 (IV), resulting in the Roman numeral "MCMXCIV" [^2]. ### Explanation of Subtractive Notation Handling Subtractive notation is used in specific cases where a smaller numeral precedes a larger one, indicating subtraction rather than addition. These cases include: - IV for 4 (5 - 1) - IX for 9 (10 - 1) - XL for 40 (50 - 10) - XC for 90 (100 - 10) - CD for 400 (500 - 100) - CM for 900 (1000 - 100) By including these subtractive combinations in the `val` and `syms` arrays, the function ensures that the correct Roman numeral representation is generated without requiring additional logic to handle these cases separately [^3]. ### Example Usage For instance, if you call `int_to_roman(1994)`, the function will return `"MCMXCIV"`, which accurately represents the year 1994 in Roman numerals [^2]. Similarly, calling `int_to_roman(58)` will return `"LVIII"`, representing 58 as L (50), V (5), and III (3).
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值