Разница в скорости при использовании встроенных строк против конкатенации в php5?
(предположим, что php5) рассмотрим
<?php
$foo = 'some words';
//case 1
print "these are $foo";
//case 2
print "these are {$foo}";
//case 3
print 'these are ' . $foo;
?>
Есть ли большая разница между 1 и 2?
Если нет, то между 1/2 и 3?
Ответы
Ответ 1
Ну, как и во всех вопросах "Что может быть быстрее в реальной жизни", вы не можете побить реальный тест на жизнь.
function timeFunc($function, $runs)
{
$times = array();
for ($i = 0; $i < $runs; $i++)
{
$time = microtime();
call_user_func($function);
$times[$i] = microtime() - $time;
}
return array_sum($times) / $runs;
}
function Method1()
{
$foo = 'some words';
for ($i = 0; $i < 10000; $i++)
$t = "these are $foo";
}
function Method2()
{
$foo = 'some words';
for ($i = 0; $i < 10000; $i++)
$t = "these are {$foo}";
}
function Method3()
{
$foo = 'some words';
for ($i = 0; $i < 10000; $i++)
$t = "these are " . $foo;
}
print timeFunc('Method1', 10) . "\n";
print timeFunc('Method2', 10) . "\n";
print timeFunc('Method3', 10) . "\n";
Дайте ему несколько прогонов, чтобы перечислить все, а затем...
0.0035568
0.0035388
0.0025394
Итак, как и ожидалось, интерполяция практически идентична (различия уровня шума, возможно, из-за дополнительных символов, которые должен обрабатывать механизм интерполяции). Прямая конкатенация составляет около 66% скорости, что не вызывает большого шока. Интерполяционный парсер будет выглядеть, ничего не поделать, а затем завершить с помощью простой внутренней строки concat. Даже если concat был дорогим, интерполятору все равно придется это делать, после всю работу, чтобы разобрать переменную и обрезать/скопировать исходную строку.
Обновления от Somnath:
Я добавил Method4() к логике реального времени.
function Method4()
{
$foo = 'some words';
for ($i = 0; $i < 10000; $i++)
$t = 'these are ' . $foo;
}
print timeFunc('Method4', 10) . "\n";
Results were:
0.0014739
0.0015574
0.0011955
0.001169
Если вы просто объявляете только строку и не нуждаетесь в синтаксическом анализе этой строки, то зачем путать отладчик PHP для разбора. Надеюсь, вы поняли мою точку зрения.
Ответ 2
Разница в производительности была неактуальной с по крайней мере в январе 2012 года и, вероятно, раньше:
Single quotes: 0.061846971511841 seconds
Double quotes: 0.061599016189575 seconds
Раньше версии PHP, возможно, имели значение - я лично предпочитаю одинарные кавычки для двойных кавычек, поэтому это была удобная разница. Заключение статьи дает отличную оценку:
Никогда не доверяйте статистике, которую вы не создали.
(Хотя в статье цитируется фраза, оригинальная фраза скорее всего была ложно отнесена к Уинстону Черчиллю, изобретенному службой пропаганды Джозефа Геббельса, чтобы изобразить Черчилль как лжец:
Ich traue keiner Statistik, die ich nicht selbst gefälscht habe.
Это свободно переводит: "Я не доверяю статистике, которую я не подделывал сам." )
Ответ 3
Текущие тесты:
http://phpbench.com/
На самом деле существует тонкая разница при объединении переменных с одиночными или двойными кавычками.
Ответ 4
Используемый тест ADAM
"these are " . $foo
обратите внимание на следующее:
'these are ' . $foo;
это связано с тем, что вычисляется двойная кавычка "строка", где только одна строка "строка" принимается так же, как...
Ответ 5
Не пытайтесь оптимизировать строковые операции в PHP. Конкатенация против интерполяции бессмысленна (в реальном мире), если ваши запросы к базе данных плохо написаны или вы не используете какую-либо схему кэширования. Напишите свои строковые операции таким образом, чтобы отладка кода позже была простой, различия в производительности незначительны.
@uberfuzzy Предполагая, что это всего лишь вопрос о языковой миниатюре, я полагаю, это хорошо. Я просто пытаюсь добавить к разговору, что сравнение производительности между одиночной кавычкой, двойной кавычкой и heredoc в приложениях реального мира бессмысленно по сравнению с реальными поглотителями производительности, такими как плохие запросы к базе данных.
Ответ 6
Любые различия во времени выполнения полностью ничтожны.
См.
Не тратьте время на такие микро-оптимизации. Используйте профилировщик для измерения производительности вашего приложения в реальном мире, а затем оптимизируйте, где это действительно необходимо. Оптимизация одного неактивного DB-запроса, скорее всего, приведет к увеличению производительности, чем применение микро-оптимизаций по всему вашему коду.
Ответ 7
Кажется, я помню, что разработчик программного обеспечения форума Vanilla заменил все двойные кавычки в своем коде одиночными кавычками и заметил разумное увеличение производительности.
Я пока не могу найти ссылку на обсуждение в данный момент.
Ответ 8
существует разница при объединении переменных... и то, что вы делаете с результатом... и если то, что вы делаете, это сброс на вывод, это или не выводит буферизацию.
также, что такое ситуация с памятью сервера? обычно управление памятью на платформе более высокого уровня хуже, чем на более низких платформах...
$a = 'parse' . $this;
управляет памятью на уровне платформы пользовательского кода...
$a = "parse $this";
управляет памятью на уровне платформы платформы php...
поэтому эти тесты, связанные с ЦП, не рассказывают всю историю.
запуск теста в 1000 раз против запуска теста 1000 раз на сервере, который пытается запустить такое же моделирование 1000 раз одновременно... вы можете получить совершенно разные результаты в зависимости от области применения.
Ответ 9
Двойные кавычки могут быть намного медленнее. Я читал из нескольких мест, что лучше сделать это
'parse me '.$i.' times'
чем
"parse me $i times"
Хотя я бы сказал, что второй дал вам более читаемый код.
Ответ 10
Практически нет никакой разницы! См. Тайминги: http://micro-optimization.com/single-vs-double-quotes
Ответ 11
Просто добавьте что-то еще в микс, если вы используете переменную внутри синтаксиса с двойной кавычкой:
$foo = "hello {$bar}";
быстрее, чем
$foo = "hello $bar";
и оба они быстрее, чем
$foo = 'hello' . $bar;
Ответ 12
Следует отметить, что при использовании модифицированной версии примера Адама Райта с 3 переменными результаты меняются на противоположные и первые две функции выполняются быстрее, последовательно. Это с PHP 7.1 на CLI:
function timeFunc($function, $runs)
{
$times = array();
for ($i = 0; $i < $runs; $i++)
{
$time = microtime();
call_user_func($function);
@$times[$i] = microtime() - $time;
}
return array_sum($times) / $runs;
}
function Method1()
{
$foo = 'some words';
$bar = 'other words';
$bas = 3;
for ($i = 0; $i < 10000; $i++)
$t = "these are $foo, $bar and $bas";
}
function Method2()
{
$foo = 'some words';
$bar = 'other words';
$bas = 3;
for ($i = 0; $i < 10000; $i++)
$t = "these are {$foo}, {$bar} and {$bas}";
}
function Method3()
{
$foo = 'some words';
$bar = 'other words';
$bas = 3;
for ($i = 0; $i < 10000; $i++)
$t = "these are " . $foo . ", " . $bar . " and " .$bas;
}
print timeFunc('Method1', 10) . "\n";
print timeFunc('Method2', 10) . "\n";
print timeFunc('Method3', 10) . "\n";
Я также пробовал с "3" вместо целого числа 3, но получаю одинаковые результаты.
С $bas = 3:
0.0016254
0.0015719
0.0019806
С $bas = '3':
0.0016495
0.0015608
0.0022755
Следует отметить, что эти результаты сильно различаются (я получаю вариации около 300%), но средние значения кажутся относительно устойчивыми и почти (9 из 10 случаев) всегда показывают более быстрое выполнение для 2 первых методов, с методом 2 всегда немного быстрее, чем метод 1.
В заключение: то, что верно для одной единственной операции (будь то интерполяция или конкатенация), не всегда верно для комбинированных операций.