leetCode算法題:羅馬數字轉整數。
要求:
Given a roman numeral, convert it to an integer.
Input is guaranteed to be within the range from 1 to 3999.
一開始看到這道題的時候,發現它的通過率還是蠻高,想着應該還是很簡單的。可是發現真正在寫代碼的時候有很多很多問題出現。差不多花了我一天的事件吧,才搞定這道題。
首先羅馬數字拼寫規則
- 羅馬數字共有7個,即
Ⅰ
(1)、Ⅴ
(5)、Ⅹ
(10)、Ⅼ
(50)、Ⅽ
(100)、Ⅾ
(500)和Ⅿ
(1000)。按照下述的規則可以表示任意正整數。需要注意的是羅馬數字中沒有“0”,與進位制無關。一般認爲羅馬數字只用來記數,而不作演算。
羅馬數字 | I | V | X | L | C | D | M |
---|---|---|---|---|---|---|---|
數字 | 1 | 5 | 10 | 50 | 100 | 500 | 1000 |
- 重複數次:一個羅馬數字重複幾次,就表示這個數的幾倍。
- 右加左減:
1. 在較大的羅馬數字的右邊記上較小的羅馬數字,表示大數字加小數字。
2. 在較大的羅馬數字的左邊記上較小的羅馬數字,表示大數字減小數字。
3. 左減的數字有限制,僅限於I
、X
、C
。比如45不可以寫成VL
,只能是XLV
。
4. 但是,左減時不可跨越一個位值。比如,99不可以用IC
( 100-1)表示,而是用XCIX
([100-10]+[10-1])表示。(等同於阿拉伯數字每位數字分別表示。)
5. 左減數字必須爲一位,比如8寫成VIII
,而非IIX
。
6. 右加數字不可連續超過三位,比如14寫成XIV,而非XIIII
。(見下方“數碼限制”一項。)
- 加線乘千:
1. 在羅馬數字的上方加上一條橫線或者加上下標的Ⅿ
,表示將這個數乘以1000
,即是原數的1000
倍。
2. 同理,如果上方有兩條橫線,即是原數的1000000
(1000^2)
倍。
- 數碼限制:
1. 同一數碼最多隻能連續出現三次,如40不可表示爲XXXX
,而要表示爲XL
。
2. 例外:由於IV是古羅馬神話主神朱庇特(即IVPITER
,古羅馬字母裏沒有J
和U
)的首字,因此有時用IIII
代替IV
。
思路
- 我們可以用兩個變量保存當前數字和之前的數字就行了。
- 如果當前數字是最後一個數字,或者之後的數字比它小的話,則加上當前數字
- 其他情況則減去這個數字
這樣思路做下去我覺得還是一種不是很麻煩的方法。
代碼
nt romanToInt(char* s) {
int i = 0;
int sum = 0;
int size,temp,flag;
while (s[i] != '\0'){
i++;
}
size = i;
for(i = 0;i<size;i++){
switch (s[i]){
case 'I':temp = 1;
break;
case 'V':temp = 5;
break;
case 'X':temp = 10;
break;
case 'L':temp = 50;
break;
case 'C':temp = 100;
break;
case 'D':temp = 500;
break;
case 'M':temp = 1000;
break;
}
switch (s[i+1]){
case 'I':flag = 1;
break;
case 'V':flag = 5;
break;
case 'X':flag = 10;
break;
case 'L':flag = 50;
break;
case 'C':flag = 100;
break;
case 'D':flag = 500;
break;
case 'M':flag = 1000;
break;
}
if(i==size-1 || flag<=temp){
sum += temp;
}else{
sum -= temp;
}
}
return sum;
}
因爲我用的是c語言,所以需要很多switch解決處理,但是如果說用java的話,可以使用map就簡單很多了!