处理字符串是否是ip的三个函数:
<?php
function isValidIpAddressV1(String $ipAddress){
if(empty($ipAddress)){
return false;
}
$regex = "/^(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|[1-9])\\.(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\.(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\.(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)$/";
$ret = preg_match($regex, $ipAddress,$matches);
return is_bool($ret)?$ret:($ret>0?true:false);
}
function isValidIpAddressV2(String $ipAddress) {
if(empty($ipAddress)){
return false;
}
$ipUnits = explode('.',$ipAddress);
if (count($ipUnits) != 4) {
return false;
}
for ($i = 0; $i < 4; ++$i) {
$ipUnitIntValue = 0;
try {
$ipUnitIntValue = intval($ipUnits[$i]);
} catch (\Exception $e){
return false;
}
if ($ipUnitIntValue < 0 || $ipUnitIntValue > 255) {
return false;
}
if ($i == 0 && $ipUnitIntValue == 0)
{
return false;
}
}
return true;
}
function isValidIpAddressV3(String $ipAddress){
$ipChars = str_split($ipAddress);
$length = count($ipChars);
$ipUnitIntValue = -1;
$isFirstUnit = true;
$unitsCount = 0;
for ($i=0; $i < $length; $i++) {
$c = $ipChars[$i];
if ($c == '.') {
if ($ipUnitIntValue < 0 || $ipUnitIntValue > 255) return false;
if ($isFirstUnit && $ipUnitIntValue === 0) return false;
if ($isFirstUnit) $isFirstUnit = false;
$ipUnitIntValue = -1;
$unitsCount++;
continue;
}
if ($c < '0' || $c > '9') {
return false;
}
if ($ipUnitIntValue == -1) $ipUnitIntValue = 0;
$ipUnitIntValue = $ipUnitIntValue * 10 + ($c - '0');
}
if ($ipUnitIntValue < 0 || $ipUnitIntValue > 255) return false;
if ($unitsCount != 3) return false;
return true;
}
第一种实现方式利用的是正则表达式,写出完全没有 bug 的正则表达本身就比较有挑战。所以,从 KISS 原则的设计初衷上来讲,这种实现方式并不符合 KISS 原则。第二种实现方式使用了现成的字符串函数,来处理 IP 地址。第三种实现方式通过逐一处理 IP 地址中的字符,来判断是否合法。从代码行数上来说,这两种方式差不多。但是,第三种要比第二种更加有难度,更容易写出 bug。从可读性上来说,第二种实现方式的代码逻辑更清晰、更好理解。所以,在这两种实现方式中,第二种实现方式更加“简单”,更加符合 KISS 原则。