LeetCode : Roman to Integer
题目原意:将罗马数字转化为十进制数字输出
这道题的难度其实在于,罗马数字的读法。
1、相同的数字连写,所表示的数等于这些数字相加得到的数,如:Ⅲ = 3;
2、小的数字在大的数字的右边,所表示的数等于这些数字相加得到的数, 如:Ⅷ = 8;Ⅻ = 12;
3、小的数字,(限于Ⅰ、X 和C)在大的数字的左边,所表示的数等于大数减小数得到的数,如:Ⅳ= 4;Ⅸ= 9;
我们可以总结,若当前数字(可能是连续数字)比前一个数字小,则减去当前数字,反之,都是加。
代码如下(leetCode 测得运行时间为12ms):
int romanToInt(char *s)
{
int k = 1;
int sToInt = 0; //!< 保存返回值
int i = strlen(s) - 1;
int value_now = 0; //!< 保存当前字符对应的值
int value_pred = 0; //!< 保存前一个字符对应的值
while (i >= 0)
{
while (s[i] == s[i-1]) //!< 读取连续的字符
{
++k;
--i;
}
if ( (value_now = romanToNum(s[i])) > value_pred) //!< 判断当前字符与前一个不同字符的大小关系
{
sToInt = sToInt + k * value_now; //!< now > pred
value_pred = value_now;
k = 1;
--i;
}
else
{
sToInt = sToInt - k * value_now; //!< now < pred
value_pred = value_now;
--i;
}
}
return sToInt;
}
int romanToNum(char s) //!< 将罗马字符s转化为对应的十进制数
{
int value = 0;
switch (s)
{
case 'I':
value = 1;
break;
case 'V':
value = 5;
break;
case 'X':
value = 10;
break;
case 'L':
value = 50;
break;
case 'C':
value = 100;
break;
case 'D':
value = 500;
break;
case 'M':
value = 1000;
break;
default:
break;
}
return value;
}