对我来说,一个有效的域是我可以注册的东西,或者至少是看起来我可以注册的东西。这就是我喜欢将其与“localhost”-names 分开的原因。
最后我对主要问题感兴趣,如果避免使用正则表达式会更快,这是我的结果:
<?php
function filter_hostname($name, $domain_only=false) {
// entire hostname has a maximum of 253 ASCII characters
if (!($len = strlen($name)) || $len > 253
// .example.org and localhost- are not allowed
|| $name[0] == '.' || $name[0] == '-' || $name[ $len - 1 ] == '.' || $name[ $len - 1 ] == '-'
// a.de is the shortest possible domain name and needs one dot
|| ($domain_only && ($len < 4 || strpos($name, '.') === false))
// several combinations are not allowed
|| strpos($name, '..') !== false
|| strpos($name, '.-') !== false
|| strpos($name, '-.') !== false
// only letters, numbers, dot and hypen are allowed
/*
// a little bit slower
|| !ctype_alnum(str_replace(array('-', '.'), '', $name))
*/
|| preg_match('/[^a-z\d.-]/i', $name)
) {
return false;
}
// each label may contain up to 63 characters
$offset = 0;
while (($pos = strpos($name, '.', $offset)) !== false) {
if ($pos - $offset > 63) {
return false;
}
$offset = $pos + 1;
}
return $name;
}
?>
与velcrow 's function 和 10000 次迭代相比的基准测试结果(complete results 包含许多代码变体。找到最快的很有趣。):
filter_hostname($domain);// $domains: 0.43556308746338 $real_world: 0.33749794960022
is_valid_domain_name($domain);// $domains: 0.81832790374756 $real_world: 0.32248711585999
$real_world 不包含超长域名以产生更好的结果。现在我可以回答你的问题了:使用ctype_alnum() 可以在没有正则表达式的情况下实现它,但由于preg_match() 更快,我更喜欢这样。
如果您不喜欢“local.host”是有效域名这一事实,请使用this function,而不是对公共 tld 列表有效。也许有人找到时间将两者结合起来。