检测数字字符串的方法is_numeric与ctype_digit的区别

  •   
  • 4356
  • PHP
  • 0
  • super_dodo
  • 2013/09/30

假如我们需要对用户提交过来的数组做检查,对于某些字段只允许提交数值类型(十进制),我们就需要对提交过来的数值进行判断

//用户提交的值有:
$tests = array("-1","0","42",1337,"1e4",9.1,"0x7","0xA","07","0x8","not numeric",array());

//方法1:使用is_numeric()
foreach($tests as $element){
	if(is_numeric($element)){		
		echo "{$element}===> is numeric<hr>";
	}else{
		echo "{$element}===> is NOT numeric<hr>";
	}
}
//返回值:		
-1===> is numeric
0===> is numeric
42===> is numeric
1337===> is numeric
1e4===> is numeric
9.1===> is numeric
0x7===> is numeric
0xA===> is numeric
07===> is numeric
0x8===> is numeric
not numeric===> is NOT numeric
Array===> is NOT numeric
//小结:使用is_numeric()方法会存在问题一些隐藏的风险。
//科学计数法(1e4),十六进制(0xA),小数(9.1),负数(-1)等都会认为是数值,返回值为true


//方法2:使用ctype_digit()
foreach ($tests as $element) {	
	if(ctype_digit($element)){
		echo "{$element}===> is numeric<hr>";
	}else{
		echo "{$element}===> is NOT numeric<hr>";
	}
}	
//返回值为:
-1===> is NOT numeric
0===> is numeric
42===> is numeric
1337===> is numeric
1e4===> is NOT numeric
9.1===> is NOT numeric
0x7===> is NOT numeric
0xA===> is NOT numeric
07===> is numeric
0x8===> is NOT numeric
not numeric===> is NOT numeric
Array===> is NOT numeric

//小结:使用ctype_digit()比较严谨一点。
//但是八进制,二进制是单纯以0开头的,07、01默认也是数值类型的。

//还有需要注意intval这个方法,会把字符串转换0或者,数值。直接上代码:
echo intval('asdbasdb');		// 0
echo intval('23agsgda');		// 23

<script type="text/javascript">	
	//前端可以用javascript正则进行判断
	var cpu = $.trim($("#cpu").val());
	var mem = $.trim($("#mem").val());
		
	var reg = /^[0-9]{1,}$/;
	if(!reg.test(cpu)){ alert('CPU核数只能为数字!!'); return false;}
	if(!reg.test(mem)){ alert('内存大小只能为数字!!'); return false;}
</script>

建议:比较严谨的操作是,先前端Javascript进行检测,再进行后端(包括框架的过滤)的检测,最后数据库的字段类型守住关卡。前端检测严格的后,后端可以使用is_numeric()。如果需要更严谨且防止跳过前端检测,则后端建议用ctype_digit()。

The world breaks everyone and afterward many are strong at the broken places. 这世界会打击每一个人,但经历过后,许多人会在受伤的地方变得更坚强。—— Ernest Hemingway 海明威(美国作家)