剑指offer面试题20——表现数值的字符串

题目:请实现一个函数用来判断字符串是否表示数值(包括整数和小数)。例如,字符串“+100”、“5e2”、“-123”、“3.1416”及“-1E-16”都表示数值,但“12e”、“1a3.14”、“1.2.3”、“+-5”以及“12e+5.4”都不是。

思路:

       这道题很考验细节的处理和分析。首先要知道什么样的表示方法才是对的,才能够去进行判断。首先整数部分不是必要的,但是如果没有整数部分,那么小数部分就不能为空。还有小数点后面可以没有数字,小数点前面也可以没有数字。指数的前后都必须有整数才能正确地表示数字,这些情况都要考虑到。然后按照逐个字符进行比对,来判断这个字符串是否表示数值。

  1. 首先判断有没有整数部分,用numeric来记录true或者false;
  2. 再判断有没有小数点,以及小数点后面有没有数字;
  3. 再判断有没有指数,指数后面有没有整数。

代码:

bool scanUnsignedInteger(const char** str)
{
	const char*before = *str;
	while (**str!='\0'&&**str>'0'&&**str<='9')
	{
		++(*str);
	}
	//当str中存在若干0~9的数字时,返回true
	return *str > before;
}

bool scanInteger(const char**str)
{
	if (**str == '+' || **str == '-')
		++(*str);
	return scanUnsignedInteger(str);
}

bool isNumeric(const char*str)
{
	if (str == nullptr)
		return false;
	bool numeric = scanInteger(&str);//&传入的是地址,这里不是引用的意思
	//如果出现‘.',则接下来是数字的小数部分
	if (*str == '.')
	{
		++str;
		//下面一行代码用||的原因:
		//1.小数可以没有整数部分,如.123等于0.123;
		//2.小数点后面可以没有数字,如233.等于233.0
		//3.小数点前后可以都有数字如233.666
		numeric = scanInteger(&str) || numeric;
	}
	//如果出现‘e'或者'E',则接下来是数字的指数部分
	if (*str == 'e' || *str == 'E')
	{
		++str;
		//下面一行代码用&&的原因:
		//1.当e或者E前面没有数字时,整个字符串不能表示数字,如.e1、e1;
		//2.当e或者E后面没有整数时,整个字符串不能表示数字,如12e、12e+5.4;
		numeric = numeric && scanInteger(&str);
	}
	return numeric && *str == '\0';
}

复习:

        思路如上面说的,要注意的是检查数字的时候传入的是指针的引用,因为要改变指针指向的位置,如果传入的是指针,那么只是实参指针的复制,函数运行结束之后,不会改变原指针的指向位置。

 

二刷代码:

bool scanUnsignedInterger(const char** str)
{
	const char* before = *str;
	while (**str>='0'&&**str<='9'&&**str!='\0')
	{
		++(*str);
	}

	return *str > before;

}

bool scanSignedInteger(const char** str)
{
	if (**str == '-' || **str == '+')
		++(*str);
	return scanUnsignedInterger(str);
}

bool isNumeric(const char*str)
{
	if (str == nullptr)
		return false;
	bool isNumeric = scanSignedInteger(&str);
	if (*str == '.')
	{
		++str;
		isNumeric = isNumeric || scanUnsignedInterger(&str);
	}
	if (*str == 'e' || *str == 'E')
	{
		++str;
		isNumeric = isNumeric && scanUnsignedInterger(&str);
	}
	return isNumeric && *str == '\0';
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值