Ответ 1
Этот поток abit old, но я сделал несколько тестов, связанных с вопросом, поэтому я мог бы также опубликовать его:
Код тестирования (PHP 5.3.3 - выпуск CentOS 6.5 (Final)):
class NonExistant
{
protected $associativeArray = array(
'one' => 'one',
'two' => 'two',
'three' => 'three',
'four' => 'four',
'five' => 'five',
'six' => 'six',
);
protected $numIterations = 10000;
public function noCheckingTest()
{
for ($i = 0; $i < $this->numIterations; $i++) {
$this->associativeArray['none'];
}
}
public function emptyTest()
{
for ($i = 0; $i < $this->numIterations; $i++) {
empty($this->associativeArray['none']);
}
}
public function isnullTest()
{
for ($i = 0; $i < $this->numIterations; $i++) {
is_null($this->associativeArray['none']);
}
}
public function issetTest()
{
for ($i = 0; $i < $this->numIterations; $i++) {
isset($this->associativeArray['none']);
}
}
public function arrayKeyExistsTest()
{
for ($i = 0; $i < $this->numIterations; $i++) {
array_key_exists($this->associativeArray['none']);
}
}
}
Результаты:
| Method Name | Run time | Difference
=========================================================================================
| NonExistant::noCheckingTest() | 0.86004090309143 | +18491.315775911%
| NonExistant::emptyTest() | 0.0046701431274414 | +0.95346080503016%
| NonExistant::isnullTest() | 0.88424181938171 | +19014.461681183%
| NonExistant::issetTest() | 0.0046260356903076 | Fastest
| NonExistant::arrayKeyExistsTest() | 1.9001779556274 | +209.73055713%
Все функции называются одинаково с помощью call_user_func()
и синхронизируются с microtime(true)
Наблюдения
empty()
и isset()
являются явными победителями других двух методов, эти два метода в значительной степени связаны с производительностью.
is_null()
работает плохо, потому что сначала нужно искать значение, почти такое же, как просто доступ к несуществующему значению $this->associativeArray['none']
, что предполагает полный поиск массива.
Однако меня удивляет производительность array_key_exists()
. Где он в 2 раза медленнее, чем empty()
и isset()
.
Примечание:
Все те функции, которые я тестировал, имеют разные применения, этот критерий доступен только для наиболее распространенного варианта использования, когда вы хотите быстро проверить значение в массиве. Мы можем рассуждать о том, следует ли считать null
"значением" или просто индикатором несуществования, но это другая тема. o.o
ОБНОВЛЕНИЕ 2017-01-20
Использовать PHP 7.1
Исправлена ошибка, отмеченная @bstoney
$ php -v
PHP 7.1.0 (cli) (built: Dec 2 2016 03:30:24) ( NTS )
Copyright (c) 1997-2016 The PHP Group
Zend Engine v3.1.0-dev, Copyright (c) 1998-2016 Zend Technologies
$ php -a
php > $a = ['one' => 1, 'two' => 2, 'three' => 3];
php > $numIterations = 1000000;
php > $start = microtime(true); for ($i = 0; $i < $numIterations; $i++) { $a['none']; }; echo microtime(true) - $start;
0.43768811225891
php > $start = microtime(true); for ($i = 0; $i < $numIterations; $i++) { empty($a['none']); }; echo microtime(true) - $start;
0.033049821853638
php > $start = microtime(true); for ($i = 0; $i < $numIterations; $i++) { is_null($a['none']); }; echo microtime(true) - $start;
0.43995404243469
php > $start = microtime(true); for ($i = 0; $i < $numIterations; $i++) { isset($a['none']); }; echo microtime(true) - $start;
0.027907848358154
php > $start = microtime(true); for ($i = 0; $i < $numIterations; $i++) { array_key_exists('none', $a); }; echo microtime(true) - $start;
0.049405097961426