[1日に1つの質問]ローマ数字から整数へ

https://leetcode-cn.com/problems/roman-to-integer/ ローマ
数字から整数へ
ローマ数字には、I、V、X、L、C、D、Mの7文字が含まれています。

文字値
I 1
V 5
X 10
L 50
C 100
D 500
M 1000
たとえば、ローマ数字2はIIと表記され、2つの平行1です。12はXIIと表記され、X + IIです。27 XXVIIと書きます。XX+ V + IIです。

通常、ローマ数字の小さい数字は大きい数字の右側にあります。ただし、特殊なケースがあります。たとえば、4はIIIIではなくIVと表記されます。数1は数5の左側にあり、表される数は数1を数5だけ減じることによって得られる数4に等しい。同様に、数字9はIXとして表されます。この特別なルールは、次の6つの状況にのみ適用されます。

V(5)とX(10)の左側に配置して、4と9を表すことができます。
XはL(50)とC(100)の左側に配置して、40と90を示すことができます。
CはD(500)とM(1000)の左側に配置して、400と900を示すことができます。
ローマ数字を指定して、整数に変換します。入力は1から3999の範囲でなければなりません。

例1:

入力: "III"
出力:3
例2:

入力: "IV"
出力:4
例3:

入力: "IX"
出力:9
例4:

入力: "LVIII"
出力:58
説明:L = 50、V = 5、III = 3
例5:

入力: "MCMXCIV"
出力:1994
説明:M = 1000、CM = 900、XC = 90、IV = 4。


解決策1

マップを使用します。
キーはローマ数字の1文字で、valは対応する値です。
今のval以下のような次のキーに対応するvalを、以下ではありませんどのように対応するキーを決定する必要があるIV4の代わりに、6を。
40ms 9.1mb、マップの構築に時間がかかる、以下の操作時間の複雑さはO(n)です。

class Solution {
public:
    int romanToInt(string s) {
        map<char, int> m = {
        	{'I', 1},
        	{'V', 5},
        	{'X', 10},
        	{'L', 50},
        	{'C', 100},
        	{'D', 500},
        	{'M', 1000},
        };

        int ret = 0;
        for (int i = 0; i < s.size(); ++i) {
        	if (m[s[i]] < m[s[i + 1]]) {
        		ret = ret - m[s[i]];
        	} else {
        		ret = ret + m[s[i]];
        	}
        }

        return ret;
    }
};

解決策2

ネチズンのソリューションは、4ms 5.6mb、

#define nI 1  //直接用define I 1,好像会有歧义
#define nV 5 
#define nX 10
#define nL 50
#define nC 100
#define nD 500
#define nM 1000

int romanToInt(char* s) 
{ 
    int num = 0, flag = 0;   /*立一个flag,是因为之前我在后面会用三个if,一个else,其实我的初衷是三个if有其中任何一个满足都不要再执行else了
	                         但是如果没有flag的话,意思是第三个if如果不成立便会跳去else,比如IV,第一个if满足,然后第三个if不满足,else这时候
							 就会出来执行,很不爽*/
    while(*s != NULL)
    {
        if(*s == 'I' && (*(s + 1) == 'V' || *(s + 1) == 'X'))     //接下来的这三个if都有特殊含义,所以flag=1,普通情况属于flag=0
        {
			flag = 1;
            switch(*(s + 1))
            {
                case 'V':num += (nV - nI); s+=2; break;
                case 'X':num += (nX - nI); s+=2; break;
            }
        }
        if(*s == 'X' && (*(s + 1) == 'L' || *(s + 1) == 'C'))
        {
			flag = 1;
            switch(*(s + 1))
            {
                case 'L':num += (nL - nX); s+=2; break;
                case 'C':num += (nC - nX); s+=2; break;
            }
        }
        if(*s == 'C' && (*(s + 1) == 'D' || *(s + 1) == 'M'))
        {
			flag = 1;
            switch(*(s + 1))
            {
                case 'D':num += (nD - nC); s+=2; break;
                case 'M':num += (nM - nC); s+=2; break;
            }
        }
        if(flag == 0)   //本来这里是else的,改为if(flag == 0)
        {
            switch(*s)
            {
                case 'I':num += nI; s += 1; break;
                case 'V':num += nV; s += 1; break;
                case 'X':num += nX; s += 1; break;
                case 'L':num += nL; s += 1; break;
                case 'C':num += nC; s += 1; break;
                case 'D':num += nD; s += 1; break;
                case 'M':num += nM; s += 1; break;
            }
        }
		flag = 0;  //最后置回普通状态
    }
    return num;
}

EOF

98件のオリジナル記事が公開されました 91件の賞賛 40,000回以上の閲覧

おすすめ

転載: blog.csdn.net/Hanoi_ahoj/article/details/105299608