Ex20 表示数字的字符串
题目描述
请实现一个函数用来判断字符串是否表示数值(包括整数和小数)。例如,字符串”+100”、”5e2”、”-123”、”3.1416”、”-1E-16”、”0123”都表示数值,但”12e”、”1a3.14”、”1.2.3”、”+-5”及”12e+5.4”都不是。
解题思路
采用类似于分治的思想。具体如下:
- 如果有一个小数点,则前面是一个integer,后面是一个unsigned integer。
- 如果有一个e,前面的应是一个float(参见上),后面是一个unsigned integer。
另外,LeetCode上有很多刁钻的case,举例如下:
“1 “
“1.”
“.1”
”.”
”.+”
做题的时候应该考虑到。以下的代码参考了《剑指Offer》的实现。
代码
bool is_uint (char **ps);
bool is_int (char **s);
bool
isNumber (char *s)
{
if (s == NULL)
return false;
while (*s == ' ')
s++;
bool num = is_int (&s);
if (*s == '.')
{
s++;
num = is_uint (&s) || num;
}
if (*s == 'e' || *s == 'E')
{
s++;
num = is_int (&s) && num;
}
while (*s == ' ')
s++;
return num && *s == '\0';
}
bool
is_uint (char **ps)
{
const char *before = *ps;
while (**ps >= '0' && **ps <= '9')
(*ps)++;
return *ps > before;
}
bool
is_int (char **s)
{
if (**s == '+' || **s == '-')
(*s)++;
return is_uint (s);
}
结果
执行结果:通过
执行用时:4 ms, 在所有 C 提交中击败了62.52%的用户
内存消耗:5.4 MB, 在所有 C 提交中击败了6.24%的用户
备注
LeetCode对C/C++内存越界检查是用的AddressSanitizer,对于我这种对这些事情只求大概的人来讲,使用这个还是可以使得代码变得更安全,更达到工业级水准。以GCC为例展示如下。
gcc main.c -o ex20 -fsanitize=address -g