我尝试编写一个可以区分以下四种不同错误的代码。
TypeError
:第一个参数不是整数; TypeError
:第二个参数不是字符串; ValueError
:第一个参数的值不在1
到13
的范围内;或ValueError
:第二个参数的值不是集{'s', 'h', 'c', 'd'}
中的其中一个字符串。但是,我只能让第一个工作,而不是其他三个错误。我尝试了不同的方法让它发挥作用,但仍然无法弄清楚是什么错误。
class Card: # One object of class Card represents a playing card
rank = ['','Ace','Two','Three','Four','Five','Six','Seven','Eight','Nine','Ten','Jack','Queen','King']
suit = {'d':'Diamonds', 'c':'Clubs', 'h':'Hearts', 's':'Spades'}
def __init__(self, rank=2, suit=0): # Card constructor, executed every time a new Card object is created
if type(rank) != int:
raise TypeError()
if type(suit) != str:
raise TypeError()
if rank != self.rank:
raise ValueError()
if suit != 'd' or 'c' or 'h' or 's':
raise ValueError()
self.rank = rank
self.suit = suit
def getRank(self): # Obtain the rank of the card
return self.rank
def getSuit(self): # Obtain the suit of the card
return Card.suit[self.suit]
def bjValue(self): # Obtain the Blackjack value of a card
return min(self.rank, 10)
def __str__(self): # Generate the name of a card in a string
return "%s of %s" % (Card.rank[int(self.rank)], Card.suit[self.suit])
if __name__ == "__main__": # Test the class Card above and will be skipped if it is imported into separate file to test
try:
c1 = Card(19,13)
except TypeError:
print ("The first parameter is not an integer")
except TypeError:
print ("The second parameter is not a string")
except ValueError:
print ("The value of first parameter is not in the range of 1 to 13")
except ValueError:
print ("The value of second parameter is not one of the strings in the set {'s','h','c','d'}")
print(c1)
我知道也许是因为我有TypeError
和ValueError
。因此,Python无法区分我点击TypeError
的第二个c1 = Card(13,13)
与第一个TypeError
不同的"The first parameter is not an integer"
。所以,当我有c1 = Card(13,13)
时,我只收到{{1}}的消息。
答案 0 :(得分:1)
您正试图区分完全错误的地方中的错误来源。当错误超出Card.__init__
时,无法告诉为什么,例如抛出了TypeError
。对于每个错误类(TypeError
,ValueError
),只会触发第一个 except
:
try:
...
except TypeError:
# all TypeErrors end up here
except TypeError:
# this is *never* reached
except ValueError:
# all ValueErrors end up here
except ValueError:
# this is *never* reached
相反,当您实际Card.__init__
错误且已经知道原因是什么时,您应该在 raise
内提供具体的错误消息 :
if not isinstance(rank, int): # better than comparing to type
raise TypeError("The first parameter is not an integer")
然后你可以更简单地处理它们:
try:
c1 = Card(19,13)
except (TypeError, ValueError) as err: # assign the error to the name 'err'
print(err) # whichever we catch, show the user the message
else:
print(c1) # only print the Card if there were no errors
如果您特别需要区分同一类的不同错误,您可以明确检查消息:
except TypeError as err:
if err.args[0] == "The first parameter is not an integer":
# do whatever you need to
或创建您自己的,更具体的Exception
子类,这样您就可以拥有单独的except
块:
class FirstParamNotIntError(Exception):
pass
(这只是一个例子,它们在您的特定情况下过于具体)。
阅读the documentation on exceptions和the tutorial on using them可能值得一读。