题目描述
请实现一个函数用来判断字符串是否表示数值(包括整数和小数)。
例如,字符串"+100"、"5e2"、"-123"、"3.1416"、"0123"都表示数值,
但"12e"、"1a3.14"、"1.2.3"、"+-5"、"-1E-16"及"12e+5.4"都不是。
解题思路
- 首先以
.
作为分割字符串,以此为主体,依照分割的个数判断数值形式
1. 分割个数若为 1
最主要的逻辑判断在此(递归主要使用此处):
(1) 判断正负符号次数
(2) 判断指数型态 e|E:不为首、若不为首前面不为正负号、判断指数的底数为整数
(3) 其馀除了正负号外,若不为数字的,则直接返回 False
(4) 最后判断 num of sign 超过2个(含)或是没有该字串没有任何数字则为 False; 其馀情况皆为 True
2. 分割个数若为 2(依序讨论)
小数点前为 A
、小数点后为 B
- 限制条件:
(1) A 存在 e|E :False
(2) B为小数点的部分,若出现正负符号则返回 False; 若出现首位为 e |E的情形,则以 ‘1’+B (e.g. B = ‘e0’; ‘1’+B = ‘1e0’) 带入递归返回结果 - 依序讨论:
(1) A空B有:返回 isNumber(B) => 回到分割数为1 的逻辑判断
(2) A有B空:返回 isNumber(A) => 回到分割数为1 的逻辑判断
(3) A有B有:加上条件,若A为单一正or负号,返回 isNumber(B); 其馀为 isNumber(A) and isNumber(B) 成立时,返回 True,其馀返回 False
(4) 其他:返回 False
3. 分割个数>2
返回False
小结
这次使用条件式判断,排除那些不成立(不过之后可以考虑列举成立的情况,其馀皆为不成立)。虽然是 Medium 的难度,但仍花了较多的时间处理众多 Special Case,蒐集如下。
- Special Case: ‘0’, ‘1 3’, ‘1 ‘, ‘6+1’, ‘.-4’, ‘+e5’,’-01’, ‘46.e3’, ‘6e.5’, ‘000e313e013’, ‘0130e+6’, ‘+E3’, ‘te1’, ‘2e0’
Python 代码
import re
class Solution:
def isNumber(self, s: str) -> bool:
# 符号的次数,超过一次即返回False
num_of_sign = 0
num_of_word = 0
# special case: 空字串
if not s:
return False
s = s.strip()
# special case: 出现两个以上的e
if len(s.split('e')) >2:
return False
# 一个空白字符 判断是否包含空白字符
if len(s) !=