方法一:1.通过hashmap来保存字符与数字之间的关系
2:根据罗马数字转整数的特点,当前字符比右边的字符小并且不是最后一个字符就说明在计算总数时该字符的符号是负,反之即为正
代码展示:
public static int romanToInt(String s){
int answer=0;
Map<Character,Integer> map=new HashMap<>(); //创建一个哈希表用来储存罗马数字与阿拉伯数字的对应关系
map.put('I',1);
map.put('V',5);
map.put('X',10);
map.put('L',50);
map.put('C',100);
map.put('D',500);
map.put('M',1000);
int s_length=s.length();
for(int i=0;i<s_length;i++){
int num=map.get(s.charAt(i));
if(i<s_length-1&&num<map.get(s.charAt(i+1))){
answer-=num;
}else {
answer+=num;
}
}
return answer;
}
根据上面提到的特点,遍历给出的字符串中的每个字符,判断是否是最后一个以及与自身右边字符的大小关系便可知道在最终答案是加还是减。
特别注意的是条件 i<s_length-1&&num<map.get(s.charAt(i+1))的顺序不能改变,因为要是改变了i+1就有可能超出字符串的范围,导致访问错误。
方法二:比方法一笨一点
1.定义两个指针i和j,j向前遍历两个字符
2.如果遍历到的两个字符是特殊的六种情况中的一个,则直接将i移动到j的位置,并直接通过switch将值加到结果中
3.如果遍历到的两个字符不是特殊的六种情况中的一个,就将j返回到i所在的位置,然后只取出当前i指向的字符,将当前i指向的这个字符的数值加到结果中
4.依次遍历完所有字符即可
public static int romanToInt(String s) {
int answer=0;
StringBuilder two_char=new StringBuilder();
int s_length=s.length();
for(int i=0,j=0;i<s_length&&j<s_length;){
two_char.replace(0,two_char.length(),"");
for(int k=0;k<2;k++){ //j向前获取两个字符
if(j<s_length){
two_char.append(s.charAt(j++)); //将获取的两个字符拼接到two_char字符串上
}else {
break;
}
}
switch (two_char.toString()){
case "IV":
answer+=4;
i=j;
break;
case "IX":
answer+=9;
i=j;
break;
case "XL":
answer+=40;
i=j;
break;
case "XC":
answer+=90;
i=j;
break;
case "CD":
answer+=400;
i=j;
break;
case "CM":
answer+=900;
i=j;
break;
default:
j=i; //当字符串不是以上的字符串时说明是单个的字符,将j返回到i的位置
char ch=s.charAt(i);
i++;
j++;
switch (ch){
case 'I':
answer+=1;
break;
case 'V':
answer+=5;
break;
case 'X':
answer+=10;
break;
case 'L':
answer+=50;
break;
case 'C':
answer+=100;
break;
case 'D':
answer+=500;
break;
case 'M':
answer+=1000;
break;
default:
break;
}
break;
}
}
return answer;
}
注意指针j所遍历到的两个字符是拼接到StringBuilder字符串后的,然后在下一次循环的时候先将StringBuilder字符串至空再拼接新的两个字符。