1. 程式人生 > >演算法習題篇之 Roman to Integer

演算法習題篇之 Roman to Integer

Roman numerals are represented by seven different symbols: I, V, X, L, C, D and M.

Symbol       Value
I             1
V             5
X             10
L             50
C             100
D             500
M             1000
For example, two is written as II in Roman numeral, just two one's added together. Twelve is written as, XII, which is simply X + II. The number twenty seven is written as XXVII, which is XX + V + II.

Roman numerals are usually written largest to smallest from left to right. However, the numeral for four is not IIII. Instead, the number four is written as IV. Because the one is before the five we subtract it making four. The same principle applies to the number nine, which is written as IX. There are six instances where subtraction is used:

I can be placed before V (5) and X (10) to make 4 and 9. 
X can be placed before L (50) and C (100) to make 40 and 90. 
C can be placed before D (500) and M (1000) to make 400 and 900.
Given a roman numeral, convert it to an integer. Input is guaranteed to be within the range from 1 to 3999.

Example 1:

Input: "III"
Output: 3
Example 2:

Input: "IV"
Output: 4
Example 3:

Input: "IX"
Output: 9
Example 4:

Input: "LVIII"
Output: 58
Explanation: L = 50, V= 5, III = 3.
Example 5:

Input: "MCMXCIV"
Output: 1994
Explanation: M = 1000, CM = 900, XC = 90 and IV = 4.

題目所說當然是很簡單的就是羅馬數字轉化為阿拉伯數字的演算法,然後我的垃圾解法就是下面這個了:

class Solution {
    public int romanToInt(String s) {
        int num = 0;
        char c1 = 'I';
        char c5 = 'V';
        char c10 = 'X';
        char c50 = 'L';
        char c100 = 'C';
        char c500 = 'D';
        char c1000 = 'M';
        String s4 = "IV";
        String s9 = "IX";
        String s40 = "XL";
        String s90 = "XC";
        String s400 = "CD";
        String s900 = "CM";
        List<String> strList = new ArrayList<String>();
        strList.add(s4);
        strList.add(s9);
        strList.add(s40);
        strList.add(s90);
        strList.add(s400);
        strList.add(s900);
        for(String str:strList){
        if(s.contains(str)){
           switch(str){
               case "IV":num+=4;break;
               case "IX":num+=9;break;
               case "XL":num+=40;break;
               case "XC":num+=90;break;
               case "CD":num+=400;break;
               case "CM":num+=900;break;
               default:break;
           }
            s = s.replace(str,"");
        }
        }
        for(int i = 0;i<s.length();i++){
            switch(s.charAt(i)){
                case 'I':num+=1;break;
                case 'V':num+=5;break;
                case 'X':num+=10;break;
                case 'L':num+=50;break;
                case 'C':num+=100;break;
                case 'D':num+=500;break;
                case 'M':num+=1000;break;
                default:break;
            }
        }

我的思路就是字串中如果有那幾個組合的話,那麼就先計算到結果裡邊,為什麼確定他們只會出現一遍,其實也蠻簡單的,因為如果有兩個五百的話不久直接用一千好了,然後兩千都以上的情況就沒有考慮。

然後算是幹活吧,蠻好理解的一種方法如下:

思路很簡單的愛,就是以鍵值的方式存到map集合裡邊,然後從後到前便利字串,如果前邊一個字母的值大於後邊的則結果剪去前邊那個字母的值,否則直接加上其值就可以了。

public static int romanToInt(String s) {
	if (s == null || s.length() == 0)
		return -1;
	HashMap<Character, Integer> map = new HashMap<Character, Integer>();
	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 len = s.length(), result = map.get(s.charAt(len - 1));
	for (int i = len - 2; i >= 0; i--) {
		if (map.get(s.charAt(i)) >= map.get(s.charAt(i + 1)))
			result += map.get(s.charAt(i));
		else
			result -= map.get(s.charAt(i));
	}
	return result;
}

對了在總結一下看到的字串操作什麼的,contains、matches、regionMatches、indexOf。

這個問題就可以迴圈來解決如果兩千以上會出現的重複的問題,當然羅馬數字應該不會就一千結束了吧,反正有重複可以用indexOf來迴圈擷取。

public class EmployeeDemo {
    //方法一:
    public int search(String str,String strRes) {//查詢字串裡與指定字串相同的個數
        int n=0;//計數器
//      for(int i = 0;i<str.length();i++) {
//         
//      }
        while(str.indexOf(strRes)!=-1) {
            int i = str.indexOf(strRes);
            n++;
            str = str.substring(i+1);
        }
        return n;
    }
    //方法二:
    public int search2(String str,String strRes) {
        int n = 0;//計數器
        int index = 0;//指定字元的長度
        index = str.indexOf(strRes);
        while(index!=-1) {
            n++;
            index = str.indexOf(strRes,index+1);
        }
         
        return n;
    }
    public static void main(String []args) {
        String arr = "朋友啊朋友,你現在怎麼樣?";
        EmployeeDemo emp = new EmployeeDemo();
        System.out.println(emp.search(arr, "朋友"));
        System.out.println(emp.search2(arr, "朋友"));
    }
}

判斷字串中特定子串的個數。