인라인 문자열을 사용할 때와 PHP5에서 연결을 사용할 때의 속도 차이는 무엇입니까?

StackOverflow https://stackoverflow.com/questions/13620

  •  08-06-2019
  •  | 
  •  

문제

(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 사이는 어떻습니까?

도움이 되었습니까?

해결책

글쎄요, 모든 "실제 생활에서 더 빠를 수 있는 것" 질문과 마찬가지로 실제 생활 테스트를 이길 수는 없습니다.

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%로 큰 충격은 아닙니다.보간 파서는 아무 작업도 수행하지 않은 다음 간단한 내부 문자열 연결로 마무리합니다.연결 비용이 많이 들더라도 보간기는 여전히 이를 수행해야 합니다. ~ 후에 변수를 구문 분석하고 원래 문자열을 잘라내거나 복사하는 모든 작업이 필요합니다.

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 디버거를 구문 분석과 혼동하는 이유는 무엇입니까?내 말을 이해하셨기를 바랍니다.

다른 팁

성능차이가 났습니다 관련 없는 적어도 2012년 1월 이후, 아마도 그 이전부터:

Single quotes: 0.061846971511841 seconds
Double quotes: 0.061599016189575 seconds

이전 버전의 PHP에는 차이가 있을 수 있습니다. 저는 개인적으로 큰 따옴표보다 작은 따옴표를 선호하므로 편리한 차이였습니다.기사의 결론은 다음과 같은 훌륭한 점을 제시합니다.

자신이 조작하지 않은 통계를 절대 신뢰하지 마십시오.

(기사에서 해당 문구를 인용했지만 원래의 퀴프는 거짓일 가능성이 높습니다. 귀속됨 처칠을 거짓말쟁이로 묘사하기 위해 조셉 괴벨스(Joseph Goebbels)의 선전 사역에 의해 고안된 윈스턴 처칠(Winston Churchill)에게:

Ich traue keiner Statistik, die ich nicht selbst gefälscht habe.

이는 대략적으로 "나는 나 자신을 속이지 않은 통계를 신뢰하지 않는다"라는 뜻입니다.)

라이브 벤치마크:

http://phpbench.com/

변수를 작은따옴표와 큰따옴표로 연결할 때 실제로는 미묘한 차이가 있습니다.

@Adam의 테스트 사용

"these are " . $foo

다음은 훨씬 더 빠릅니다.

'these are ' . $foo;

이는 큰따옴표로 묶인 "문자열"이 평가되고 작은따옴표로 묶인 '문자열'은 그대로 사용되기 때문입니다.

PHP에서 문자열 작업을 최적화하는 데 너무 집착하지 마세요.연결과 비교데이터베이스 쿼리가 제대로 작성되지 않았거나 어떤 종류의 캐싱 체계도 사용하지 않는 경우 보간은 (실제 성능에서는) 의미가 없습니다.나중에 코드를 디버깅하기 쉽고 성능 차이가 미미한 방식으로 문자열 작업을 작성하세요.

@uberfuzzy 이것이 단지 언어 세부 사항에 관한 질문이라고 가정하면 괜찮을 것 같습니다.나는 단지 열악한 데이터베이스 쿼리와 같은 실제 성능 저하와 비교할 때 실제 응용 프로그램에서 작은따옴표, 큰따옴표 및 heredoc 간의 성능을 비교하는 것이 무의미하다는 대화에 추가하려고 합니다.

실행 시간의 차이는 전혀 무시할 수 있습니다.

참조하세요

이와 같은 미세한 최적화에 시간을 낭비하지 마십시오.프로파일러를 사용하여 실제 시나리오에서 애플리케이션의 성능을 측정한 다음 실제로 필요한 부분을 최적화하세요.단일 엉성한 DB 쿼리를 최적화하는 것은 코드 전체에 미세한 최적화를 적용하는 것보다 더 큰 성능 향상을 가져올 가능성이 높습니다.

포럼 소프트웨어 개발자인 Vanilla는 자신의 코드에 있는 모든 큰따옴표를 작은따옴표로 바꾸고 합리적인 수준의 성능 향상을 발견한 것을 기억합니다.

하지만 지금은 토론에 대한 링크를 추적할 수 없는 것 같습니다.

변수를 연결할 때 차이가 있습니다.그리고 그 결과로 무엇을 하고 있는지...그리고 당신이 하고 있는 일이 그것을 출력으로 덤프하는 것이라면, 출력 버퍼링이 켜져 있거나 켜져 있지 않은 것입니다.

그리고 서버의 메모리 상황은 어떤가요?일반적으로 상위 플랫폼의 메모리 관리는 하위 플랫폼의 메모리 관리보다 더 나쁩니다.

$a = 'parse' . $this; 

사용자 코드 플랫폼 수준에서 메모리를 관리하고 있습니다.

$a = "parse $this";

PHP 시스템 코드 플랫폼 수준에서 메모리를 관리하고 있습니다.

따라서 CPU와 관련된 이러한 벤치마크는 전체 내용을 알려주지 않습니다.

벤치마크를 1000번 실행하는 것과 동일한 시뮬레이션을 동시에 1000번 실행하려고 하는 서버에서 벤치마크를 1000번 실행하는 것...응용 프로그램의 범위에 따라 크게 다른 결과를 얻을 수 있습니다.

큰따옴표는 훨씬 느릴 수 있습니다.이렇게 하는 것이 낫다는 이야기를 여러 곳에서 읽었습니다.

'parse me '.$i.' times'

~보다

"parse me $i times"

두 번째 코드가 더 읽기 쉬운 코드를 제공했다고 말하고 싶습니다.

큰따옴표로 묶인 문자열 구문 내에서 변수를 사용하는 경우 믹스에 다른 것을 추가하려면 다음을 수행하십시오.

$foo = "hello {$bar}";

보다 빠르다

$foo = "hello $bar";

둘 다보다 빠릅니다.

$foo = 'hello' . $bar; 

실제로는 전혀 차이가 없습니다!타이밍을 확인하세요: http://micro-optimization.com/single-vs-double-quotes

3개의 변수가 있는 Adam Wright의 예제의 수정된 버전을 사용하면 결과가 반전되고 처음 두 함수가 실제로 더 빠르고 일관되게 향상된다는 점에 유의해야 합니다.이는 CLI의 PHP 7.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';
    $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%의 변동이 있음) 평균은 상대적으로 안정적으로 보이며 거의(10개 사례 중 9개) 첫 번째 방법 2에 대해 항상 더 빠른 실행을 보여줍니다. 방법 2는 항상 방법 1보다 약간 빠릅니다.

결론적으로:1개의 단일 작업(보간 또는 연결)에 대해 적용되는 내용이 결합된 작업에 대해 항상 적용되는 것은 아닙니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top