Leetcode 12. Integer to Roman
Roman numerals are represented by seven different symbols:
I
,V
,X
,L
,C
,D
andM
.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 simplyX
+II
. The number twenty seven is written asXXVII
, which isXX
+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 asIV
. Because the one is before the five we subtract it making four. The same principle applies to the number nine, which is written asIX
. There are six instances where subtraction is used:
I
can be placed beforeV
(5) andX
(10) to make 4 and 9.X
can be placed beforeL
(50) andC
(100) to make 40 and 90.C
can be placed beforeD
(500) andM
(1000) to make 400 and 900.Given an integer, convert it to a roman numeral. Input is guaranteed to be within the range from 1 to 3999.
解决方法:
将数字按个十百千位存储,将每一位的每种情况都列出来,分别有小于3, 等于4, 大于5, 等于9 的情况,分别做字典来存这些情况对应的每一位字母,然后每一位遍历,代码如下:
class Solution(object):
def intToRoman(self, num):
"""
:type num: int
:rtype: str
"""
dic = {1000:'M', 'D':500, 'C':100, 'L':50, 'X':10, 'V':5, 'I':1}
dic1 = {0:"M" , 1:"C", 2:"X", 3:"I"} # val = 1
dic2 = { 0:"" , 1:"CD",2:"XL",3:"IV" } # val = 4
dic3 = { 0:"" , 1:"CM",2:"XC",3:"IX"} #val = 9
dic4 = { 0:"" , 1:"D", 2:"L", 3:"V"} # val = 5
val = [0] * 4 # M C X I
k = 1000
i = 0
result = ""
while num > 0:
val[i],num = divmod(num,k)
k = k // 10
i = i + 1
for i in range(len(val)):
while val[i] > 0:
if val[i] <= 3:
result = result + dic1[i] * val[i]
break
elif val[i] == 4:
result = result + dic2[i]
break
elif val[i] == 9:
result = result + dic3[i]
break
else:
result = result + dic4[i]
val[i] = val[i] - 5
return result
Discuss 里面的答案:
相同的想法,但是人家的代码更加精简。同时我学会了enumerate() 的用法能够节约我自己定义字典的开空间的时间,代码如下:
class Solution(object):
def intToRoman(self, num):
values = [ 1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1 ]
numerals = [ "M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I" ]
res = ""
for i, v in enumerate(values):
res += (num//v) * numerals[i]
num %= v
return res
用zip()可以更加精简:(不过时间上差距不大)
class Solution(object):
def intToRoman(self, num):
values = [ 1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1 ]
numerals = [ "M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I" ]
res = ""
for n, v in zip(numerals, values):
res += (num // v) * n
num %= v
return res
leetcode 20. Valid Parentheses
判断括号的匹配题,简单的数据结构 栈 的基本应用, 以下是我的代码:
class Solution(object):
def isValid(self, s):
"""
:type s: str
:rtype: bool
"""
dic = {"(":1, ")":-1, "[":2, "]":-2, "{":3, "}":-3}
stack = []
if len(s) == 0:
return True
if len(s) == 1:
return False
for i in range(len(s)):
if(dic[s[i]]>0):
stack.append(dic[s[i]])
else:
if (len(stack)==0) or (stack.pop() != -dic[s[i]]):
return False
if len(stack) != 0:
return False
else:
return True
发现自己的编码方式还是复杂了很多,导致了速度慢很多。以下是discuss 里面的一些较为标准速度较快的答案:
class Solution(object):
def isValid(self, s):
"""
:type s: str
:rtype: bool
"""
stack = []
length = len(s)
if(length % 2):
return False
for c in s:
if(not stack):
stack.append(c)
continue
top = stack[-1]
if(top == '('):
if(c == ')'):
stack.pop()
else:
stack.append(c)
elif(top == '['):
if(c == ']'):
stack.pop()
else:
stack.append(c)
elif(top == '{'):
if(c == '}'):
stack.pop()
else:
stack.append(c)
else:
return False
if(not stack):
return True
else:
return False
不过感觉这个不够elegant啊(你还有脸说
另外一个是leetcode官方给的代码:
class Solution(object):
def isValid(self, s):
stack = []
mapping = {")": "(", "}": "{", "]": "["}
for char in s:
if char in mapping:
top_element = stack.pop() if stack else '#'
if mapping[char] != top_element:
return False
else:
stack.append(char)
return not stack
对Dic的数据结构不熟,此处记录一下
for i in Dic:
print(i)
输出的是Dic之中的 key 值而不是value