题目:
s
思路:
虽然标签是简单题,但是我感觉比上一道中等题数字转罗马数字思路还难一点,我一开始是想从左往右,遍历整个s,但是这样一来要判断的就多了,情况很复杂,用到的if会很多,而且层层叠加,然后数组还容易超出边界。(ps这里莫名就想到了双指针,可能和之前”盛水最多容器“那题有关)然后我就利用双指针从右往左遍历,遇到字母就把对应的值放进temp_list,再用左右指针判断相邻两字母是不是4,9,40,90这种特殊情况,是的话先提前减去,例如是"IV"这种情况,left指向"I",right指向"V",那我就提前减去两个”I“对应的值,让后right =left,然后left -1,再加上一次”I“,相当于5-2+1=4,其余类似。(其实我感觉这几行代码可以重复写出来,但是我水平还不够,没有更好的书写方式)
代码:
class Solution:
def romanToInt(self, s: str) -> int:
temp_list =[]
temp_dict = {"I":1,"V":5,"X":10,"L":50,"C":100,"D":500,"M":1000}
length = len(s)
final = 0
if length == 1:
return temp_dict[s] #如果只有一个字母,返回字母对应值
right = length-1
left = length -2
while left >=0: #保证不超出边界
temp_list.append(temp_dict[s[right]]) #将当前右指针对应字母的值保存到temp_list
if (s[right] == 'V' and s[left] == 'I') or (s[right] == 'X' and s[left] == 'I'): #判断是不是”IV“或者”IX“的情形
temp_list.append(-2*temp_dict[s[left]])#是的话提前减去两倍”I“,下次遍历会加上一次”I“,所以相当于V-II+I
elif (s[right] == 'L' and s[left] == 'X') or (s[right] == 'C' and s[left] == 'X'):
temp_list.append(-2*temp_dict[s[left]])
elif (s[right] == 'D' and s[left] == 'C') or (s[right] == 'M' and s[left] == 'C'):
temp_list.append(-2*temp_dict[s[left]])
else:
pass #占位而已,比较要以else结尾,但是里面不需要写什么,就用pass占位
right = left
left -=1 #双指针向左移动一位
temp_list.append(temp_dict[s[right]]) #最左边那一位要在while结束之后加上
for i in temp_list:
final +=i
return final