PHP의 전역 변수. 함수의 PHP 변수 가시성 범위 변수 가시성

마지막 업데이트: 2015년 11월 1일

변수와 함수를 사용할 때는 변수 범위를 고려하세요. 범위는 주어진 변수의 작업 범위와 접근성을 지정합니다.

지역 변수

지역 변수는 함수 내부에서 생성됩니다. 이러한 변수는 주어진 함수 내에서만 액세스할 수 있습니다. 예를 들어:

이 경우 get() 함수는 지역 변수 $result 를 정의합니다. 그리고 일반적인 맥락에서는 이에 접근할 수 없습니다. 즉, $a = $result; $result 변수의 범위는 get() 함수에 의해 제한되므로 이는 불가능합니다. 이 함수 외부에는 $result 변수가 존재하지 않습니다.

함수 매개변수에도 동일하게 적용됩니다. 함수 외부에는 $lowlimit 및 $highlimit 매개변수도 존재하지 않습니다.

일반적으로 지역 변수는 위의 예와 같이 일부 중간 계산 결과를 저장합니다.

정적 변수

정적 변수는 지역 변수와 유사합니다. 기능이 완료된 후 해당 값이 저장된다는 점이 다릅니다. 함수가 호출될 때마다 이전에 저장된 값을 사용합니다. 예를 들어:

변수가 정적이라는 것을 나타내기 위해 static 키워드가 추가됩니다. getCounter()를 세 번 연속 호출하면 $counter 변수가 1씩 증가합니다.

$counter 변수가 일반 비정적 변수인 경우 getCounter()는 호출될 때마다 1을 인쇄합니다.

일반적으로 정적 변수는 위의 예와 같이 다양한 카운터를 만드는 데 사용됩니다.

전역 변수

때로는 변수를 전 세계 어디에서나 사용할 수 있기를 원할 때도 있습니다. 이러한 변수는 전체 프로그램에 공통된 일부 데이터를 저장할 수 있습니다. 전역 변수를 정의하려면 global 키워드를 사용하십시오:1

"; ) getGlobal(); echo $gvar; ?>

getGlobal() 함수를 호출한 후 프로그램의 어느 부분에서나 $gvar 변수에 액세스할 수 있습니다.

가변 범위해당 변수가 정의된 컨텍스트입니다. 대부분의 PHP 변수는 단일 범위를 갖습니다. 이 단일 범위(전역 범위라고도 함)에는 포함된 파일도 포함됩니다.

이 예에서 $a 변수는 포함된 스크립트(main.inc) 내에서도 사용할 수 있습니다.

지역 변수

사용자 정의 함수 정의는 다음을 지정합니다. 로컬 범위변수의 경우, 즉 함수 내에서 사용되는 모든 변수는 기본적으로 함수의 로컬 범위로 제한됩니다(정의된 함수 내에서만 사용 가능). 작동 방식: 일반 코드에 사용되는 변수와 함수에 사용되는 변수를 분리하기 위해 PHP는 각 함수 내의 변수에 대해 별도의 저장소를 제공합니다. 이러한 저장 공간 분할은 범위, 즉 변수 값을 사용할 수 있는 영역이 함수의 로컬 저장임을 의미합니다.

아래 예제는 함수 외부에서 선언된 변수가 함수 내부에서 변경되지 않음을 명확하게 보여줍니다. 함수가 어떻게 작동하는지 이해하려고 노력해서는 안 되지만, 중요한 것은 함수에 고유한 변수 세트가 있다는 것입니다.

30 ?>

이 조각을 실행하면 다음이 표시됩니다: 30.

birth() 함수 내에서 $age 변수는 1로 설정되어 있지만 이는 전역 범위에 정의된 변수와 동일하지 않습니다. 따라서 $age 변수의 값이 출력되면 원래 값인 30이 출력되는데, 지역변수는 함수 호출 시 생성되고 함수 종료 후에는 삭제된다는 점에 유의할 필요가 있다.

실제로birth() 함수 내에서 로컬 변수가 아닌 전역 변수(전역 범위에서 사용되는 변수가 호출됨)의 값을 읽거나 변경하려면 함수 정의 내에서 전역 변수로 선언해야 합니다.

참고 사항:사이트의 적응형 버전이 활성화되어 작은 크기의 브라우저에 자동으로 적응하고 쉽게 읽을 수 있도록 사이트의 일부 세부 정보를 숨깁니다. 즐겁게 시청하세요!

안녕하세요 친애하는 블로그 독자 여러분 대지에! 우리는 PHP에 함수가 있다는 것을 배웠고, 우리 자신의 함수를 만들고, 함수에 인수를 전달하고, 실행을 위해 호출하는 방법을 배웠습니다. 계속해서 PHP의 함수 주제를 다루면서 다음 사항을 강조할 필요가 있습니다.

  • 함수 내에서는 다른 함수(내장 및 사용자 정의 모두)를 포함하여 모든 PHP 코드(주기, 조건, 모든 작업)를 사용할 수 있습니다.
  • 함수 이름은 라틴 문자 또는 밑줄로 시작해야 하며 그 뒤에는 라틴 문자, 숫자 또는 밑줄이 와야 합니다.
  • 모든 함수는 전역 범위를 가집니다. 즉, 해당 함수가 다른 함수 내부에 정의되어 있더라도 어디에서나 함수를 호출할 수 있습니다.
  • PHP는 함수 오버로딩을 지원하지 않으며 생성된 함수를 재정의(변경, 추가)하거나 삭제할 수도 없습니다.
  • 함수를 사용하기 전에 정의할 필요는 없습니다. 즉, 함수를 먼저 호출한 다음 아래 코드에서 설명하면 성능에 영향을 주지 않으며 오류도 발생하지 않습니다.

조건부 함수

조건에 따라 함수를 생성(정의, 설명)할 수 있습니다. 예를 들어:

//sayHi 함수를 호출합니다. 어디서든 호출할 수 있습니다. /*sayGoodbye 함수는 아직 조건을 확인하지 않았고 if 구문 내부로 들어가지 않았기 때문에 여기서 호출할 수 없습니다.*/ if($apply)( function sayGoodbye())( echo "모두 안녕!
"; } } /*이제 sayGoodbye를 호출할 수 있습니다*/
"; }

결과:

그리고 이 예를 살펴보세요:

/*여기서 sayGoodbye를 호출하면 다음과 같은 일이 발생합니다*/안녕히 가세요(); if($apply)( function sayGoodbye())( echo "모두 안녕!
"; ) ) function sayHi())( echo "안녕하세요 여러분!
"; }

결과:

사실 제가 일해 온 만큼, 이런 건 어디서도 본 적이 없지만, 언어의 모든 가능성을 염두에 두어야 합니다.

중첩된 함수

중첩 함수는 다른 함수 내부에 선언된 함수입니다. 예:

/*sayGoodbye는 sayHi 함수를 호출한 후에만 나타나므로 여기서는 호출할 수 없습니다.*/인사하다(); /*sayHi 함수를 호출하면 어디서든 호출할 수 있습니다*/ /*이제 sayGoodbye를 호출할 수 있습니다*/안녕히 가세요(); function sayHi())( echo "안녕하세요 여러분!
"; function sayGoodbye())( echo "모두 안녕!
"; } }

다시 말하지만, 첫 번째 순회에서 PHP 인터프리터는 sayHi 함수에 대한 설명을 찾았다고 자체적으로 표시하지만 본문 내부로 들어가지는 않고 이름만 볼 수 있으며, 인터프리터가 sayHi 본문 내부로 들어가지 않기 때문에, 그러면 우리가 다른 함수(sayGoodbye) 내에서 무엇을 정의하고 있는지 전혀 알 수 없습니다.

그런 다음 코드가 실행되기 시작하고 sayHi를 호출합니다. PHP 인터프리터는 이를 실행하기 위해 sayHi 함수의 본문으로 이동해야 하며 거기서 실수로 다른 함수(sayGoodbye)에 대한 설명을 발견합니다. 그 후 sayGoodbye는 어디에서나 여러 번 호출될 수 있습니다. 당신이 원하는대로.

그러나 위 상황에서 매우 미묘한 점에 주목할 가치가 있습니다. sayHi 함수는 일회성이 됩니다. 왜냐하면 우리가 이 함수를 다시 호출하면 PHP는 다시 sayGoodbye 함수의 정의를 발견하게 되고 PHP에서는 이를 수행할 수 없기 때문입니다. this - 함수를 재정의할 수 없습니다. 나는 이전 기사에서 이것과 그것을 다루는 방법에 대해 썼습니다.

PHP에서는 위에 설명된 기술이 매우 드물게 사용되며, 예를 들어 JavaScript에서 더 자주 볼 수 있습니다.

가변 범위

PHP에는 정확히 두 가지 범위가 있습니다. 글로벌그리고 현지의. 각 프로그래밍 언어는 범위를 다르게 구성합니다. 예를 들어 C++에서는 루프에도 자체(로컬) 범위가 있습니다. 그런데 PHP에서는 이것이 전역 범위입니다. 하지만 오늘 우리는 기능에 대해 이야기하고 있습니다.

PHP의 함수에는 자체 내부 범위(로컬)가 있습니다. 즉, 함수 내의 모든 변수는 바로 이 함수 내에서만 볼 수 있습니다.

다시 한 번 말하지만, 함수 외부의 모든 것은 전역 범위이고, 함수 내부의 모든 것은 로컬 범위입니다. 예:

친애하는 전문가 여러분, 관심, 질문! 마지막 명령어는 무엇을 출력할까요? 에코 $이름; ?

직접 보셨듯이 변수는 2개였습니다. $name, 하나는 함수 내부(로컬 범위), 다른 하나는 코드 내부(전역 범위), 변수에 대한 마지막 할당 $name~였다 $name = "루드 세르게이";하지만 함수 내부에 있었기 때문에 그대로 유지되었습니다. 전역 범위에서 마지막 할당은 다음과 같습니다. $name = "안드레이";이것이 우리가 실제로 결과로 보는 것입니다.

즉, 두 개의 동일한 변수가 서로 다른 범위에서는 교차하지 않고 서로 영향을 주지 않습니다.

그림의 범위를 설명하겠습니다.

첫 번째 순회 동안 인터프리터는 전역 범위를 간략하게 검색하고 어떤 변수와 함수가 있는지 기억하지만 코드를 실행하지는 않습니다.

로컬 범위에서 전역 변수에 액세스

하지만 함수의 전역 범위에서 동일한 $name 변수에 액세스하고 액세스만 하는 것이 아니라 변경해야 한다면 어떻게 될까요? 이에 대한 3가지 주요 옵션이 있습니다. 첫 번째는 키워드를 사용하는 것입니다. 글로벌:

"; 전역 $이름; /*이제부터 전역 변수 $name*/을 의미합니다.$name = "루드 세르게이"; ) $name = "안드레이"; 안녕하세요($name); 에코 $이름; // ?

결과:

하지만 이 방법에는 단점이 있습니다. 왜냐하면 전역 변수에 접근했기 때문입니다. $name지역 변수를 잃어버렸습니다(덮어썼습니다). $name.

두 번째 방법사용하는 것입니다 PHP 슈퍼글로벌 배열. PHP 자체는 전역 범위에서 생성한 모든 변수를 이 배열에 자동으로 배치합니다. 예:

$name = "안드레이"; //동일$GLOBALS["name"] = "안드레이";

따라서:

"; $GLOBALS["name"] = "루드 세르게이"; ) $name = "안드레이"; sayHi($name); echo $name; // ?

결과는 키워드를 사용한 것과 같습니다. 글로벌:

이번에는 지역 변수, 즉 변수를 다시 작성하지 않았습니다. $name함수 내부는 동일하게 유지되고 동일합니다. "안드레이", 하지만 "루드 세르게이".

참조로 인수 전달

세 번째 방법– 주소 이전입니다( 연결) 변수의 값이 아니라 변수입니다. PHP의 링크는 다른 프로그래밍 언어와 달리 그다지 성공적이지 않습니다. 그러나 일반적으로 PHP 5.3 이상에서 지원되는 함수에 대한 참조로 인수를 전달하는 유일한 올바른 옵션을 알려 드리겠습니다. 링크를 사용하는 다른 방법이 있지만 PHP 5.2 이하에서 작동했기 때문에 PHP 개발자가 직접 링크를 포기하기로 결정했기 때문에 이에 대해 이야기하지 않겠습니다.

따라서 PHP 5.3 이상에서는 참조로 인수를 올바르게 전달하는 작업이 다음과 같이 수행됩니다.

함수 sayHi(& $name)(

함수 설명 자체에 앰퍼샌드 아이콘(&)을 추가했습니다. 이 아이콘은 변수 값을 허용하지 않고 메모리에서 이 값에 대한 링크(주소)를 허용한다는 의미입니다. PHP의 참조를 사용하면 동일한 값을 가리키는 두 개의 변수를 만들 수 있습니다. 즉, 이들 변수 중 하나가 변경되면 둘 다 변경됩니다. 왜냐하면 두 변수는 메모리에서 동일한 값을 참조하기 때문입니다.

그리고 결국 우리는:

//값이 아닌 값에 대한 참조를 허용합니다. echo "안녕하세요, ".$name."!
"; $name = "루드 세르게이"; ) $name = "안드레이"; sayHi($name); echo $name; // ?

결과:

정적 변수

다음 상황을 상상해 보세요. 총 몇 번이나 인사를 했는지 계산해야 합니다. 우리가 하려는 일은 다음과 같습니다:

"; $c++; // 카운터를 1만큼 증가시킵니다.


결과:

변하기 쉬운 $c그 의미를 기억하지 못하고 매번 새로 생성됩니다. 지역 변수를 만들어야 합니다. $c함수를 실행한 후 그 값을 기억했습니다. 이를 위해 키워드를 사용합니다. 공전:

// 카운터, 정적으로 만들어짐 echo "안녕하세요, ".$name."!
"; $c++; // 카운터를 1만큼 증가시킵니다. echo "방금 인사했어요" . $c . " 한 번.


"; ) sayHi("루드 세르게이"); sayHi("안드레이"); sayHi("드미트리");

결과:

반환 값

함수에는 값을 반환하는 등 편리한 기능이 있습니다. 이것은 함수가 화면에 무언가를 인쇄하는 대신 모든 것을 변수에 넣고 그 변수를 우리에게 제공하는 경우입니다. 그리고 우리는 이미 그것으로 무엇을 할지 결정하고 있습니다. 예를 들어 숫자를 제곱하는 이 함수를 살펴보겠습니다.

결과:

화면에 표시하는 것이 아니라 실행 결과를 반환하도록 만들어 보겠습니다. 이렇게 하려면 return 키워드를 사용하세요.

결과:

이제 우리는 이것을 다양한 방법으로 사용할 수 있습니다:

//결과를 출력한다에코 "
"; $num = getSquare(5); echo $num;

결과:

키워드를 참고해주세요 반품단순히 값을 반환하는 것이 아니라 함수, 즉 키워드 아래의 모든 코드를 완전히 중단합니다. 반품결코 성취되지 않을 것입니다. 즉, 함수에 대한 반환은 다음과 같이 작동합니다. 부서지다 for 루프:

echo "PHP는 절대 나에게 도달하지 않습니다:(";) 에코 getSquare(5); //결과를 출력한다에코 "
"; $num = getSquare(5); // 결과를 변수에 할당에코 $num; // 화면에 변수 표시

결과:

그건 반품– 이것은 또한 기능의 종료이기도 합니다. 출력을 위해서만 반환 값 없이 사용할 수 있습니다.

재귀 함수

재귀 함수는 자기 자신을 호출하는 함수입니다. 재귀는 자주 사용되지 않으며 리소스를 많이 사용하는(느린) 작업으로 간주됩니다. 그러나 재귀를 사용하는 것이 가장 분명하고 간단한 옵션입니다. 예:

"; if($숫자< 20){ // 재귀가 무한해지지 않도록 countPlease(++$number); // countPlease 함수가 자신을 호출했습니다.) ) 개수를 확인해주세요(1);

결과:

재귀 없이 수행하는 방법을 알고 있다면 그렇게 하는 것이 더 좋습니다.

PHP의 강력한 타이핑(유형 세분화)

PHP는 강력한 유형 지정을 향해 작은 조치를 취하므로 함수가 어떤 유형을 취해야 하는지 미리 지정할 수 있습니다. 유형 힌트):

결과:

포착 가능한 치명적인 오류: countPlease()에 전달된 인수 1은 주어진 정수 배열이어야 하며 7행의 /home/index.php에서 호출되고 3행의 /home/index.php에서 정의되어야 합니다.

오류는 함수가 배열을 수신할 것으로 예상하지만 대신 숫자를 전달하고 있음을 알려줍니다. 불행하게도 지금은 (배열)에 대한 유형만 지정할 수 있으며 PHP 5.4에서는 다음과 같은 옵션도 추가했습니다. 호출 가능:

호출 가능전달된 값을 함수로 호출할 수 있는지 확인합니다. Callable은 문자열 변수로 지정된 함수의 이름이거나 호출되는 객체 및 메서드의 이름일 수 있습니다. 하지만 객체와 메서드에 대해서는 나중에 이야기하겠지만(이것은 객체 지향 프로그래밍의 한 섹션입니다) 여러분은 이미 함수에 익숙합니다. 현재 PHP 5.3을 사용하고 있기 때문에 작업 결과를 보여드릴 수는 없지만 다음과 같습니다.

getEcho 함수를 호출했습니다.

가변 길이 인수 사용

마지막으로 거의 사용되지 않는 뉘앙스가 하나 더 있습니다. 상황을 상상해 보십시오. 함수에서 인수를 설명하지는 않았지만 함수에 인수를 전달합니다. 예를 들면 다음과 같습니다.

결과:

보시다시피 오류는 없지만 전달된 인수는 어디에도 사용되지 않습니다. 하지만 이것이 사라진다는 의미는 아닙니다. 여전히 함수에 전달되었으며 사용할 수 있습니다. 이를 위한 내장 PHP 함수가 있습니다:

func_num_args()- 함수에 전달된 인수의 개수를 반환합니다.
func_get_arg(시퀀스 번호)- 인수 목록에서 요소를 반환합니다.
func_get_args()- 함수 인수를 포함하는 배열을 반환합니다.

"; echo func_get_arg(0) ; ) $age = 22; getEcho("루드 세르게이", $age);

결과:

결론

오늘의 기사는 PHP의 함수 주제에 대한 마지막 기사입니다. 이제 귀하는 이 주제에 대한 귀하의 지식이 완전하다는 것을 확신할 수 있으며 귀하의 필요에 맞는 기능을 자신있게 사용할 수 있습니다.

누군가가 더 잘하고 싶지만 어떻게 해야 할지 모른다면, 가장 좋은 방법은 미리 만들어진(내장) PHP 함수를 작성하는 것입니다. 예를 들어, 자신만의 count() 함수를 작성할 수 있습니다. 또는 다른 것.

관심 가져주신 모든 분들께 감사드리며, 또 만나요! 명확하지 않은 부분이 있으면 댓글로 질문해 주세요!

변수의 범위는 변수가 정의되는 컨텍스트입니다. 대부분의 경우 모든 PHP 변수에는 범위가 하나만 있습니다. 이 단일 범위에는 포함된 파일과 필수 파일도 포함됩니다. 예를 들어:

$a = 1;
"b.inc"를 포함합니다;
?>

여기서 $a 변수는 포함된 b.inc 스크립트 내에서 사용할 수 있습니다. 그러나 사용자 정의 함수의 정의(본문)는 해당 함수의 로컬 범위를 지정합니다. 함수 내에서 사용되는 모든 변수는 기본적으로 함수의 로컬 범위로 제한됩니다. 예를 들어:

$a = 1; /* 전역 범위 */

기능 검사()
{
에코 $a ; /* 지역 범위 변수에 대한 참조 */
}

시험();
?>

echo 문이 변수 $a의 로컬 버전을 가리키고 해당 범위 내의 값이 할당되지 않았기 때문에 이 스크립트는 출력을 생성하지 않습니다. C의 전역 변수는 로컬 정의로 덮어쓰이지 않는 한 자동으로 함수에 사용할 수 있다는 점에서 C와 약간 다르다는 점을 눈치챘을 것입니다. 사람들이 실수로 전역 변수를 변경할 수 있으므로 몇 가지 문제가 발생할 수 있습니다. PHP에서 전역 변수를 함수 내에서 사용하려면 함수 정의 내에서 전역 변수로 선언해야 합니다.

예어 글로벌

먼저 사용 예 글로벌:

예제 #1 사용법 글로벌

$a = 1;
$b = 2 ;

함수 합계()
{
글로벌 $a, $b;

$b = $a + $b ;
}

합집합();
에코 $b ;
?>

위의 스크립트는 출력됩니다 3 . $a 및 $b가 함수 내에서 전역으로 정의되면 이러한 변수에 대한 모든 참조는 전역 버전을 가리킵니다. 함수가 처리할 수 있는 전역 변수의 수에는 제한이 없습니다.

전역 범위 변수에 액세스하는 두 번째 방법은 특수한 PHP 정의 배열인 $GLOBALS를 사용하는 것입니다. 이전 예제는 다음과 같이 다시 작성할 수 있습니다.

$GLOBALS는 키가 이름이고 값이 전역 변수의 내용인 연관 배열입니다. $GLOBALS는 모든 범위에 존재합니다. 이는 $GLOBALS가 슈퍼글로벌이기 때문입니다. 다음은 슈퍼전역의 기능을 보여주는 예입니다.

예제 #3 자동 전역 및 범위

함수 test_global()
{
// 대부분의 미리 정의된 변수는 그렇지 않습니다.
// "super"이며 로컬 지역에서 사용 가능
// 가시성, 함수를 지정하려면 "전역"이 필요합니다.
전역 $HTTP_POST_VARS ;

에코 $HTTP_POST_VARS["이름"];

// 슈퍼전역은 모든 범위에서 사용할 수 있습니다.
// 가시성을 가지며 "전역"을 지정할 필요가 없습니다.
// 슈퍼전역은 PHP 4.1.0부터 사용할 수 있습니다.
// HTTP_POST_VARS 사용은 더 이상 사용되지 않습니다.
echo $_POST ["이름" ];
}
?>

논평:

키워드 사용법 글로벌함수 외부에서는 오류가 아닙니다. 함수 내부에 포함된 파일에서 사용할 수 있습니다.

정적 사용( 공전) 변수

변수 범위의 또 다른 중요한 특징은 공전변하기 쉬운. 정적 변수는 함수의 로컬 범위에만 존재하지만 프로그램 실행이 해당 범위를 벗어나도 해당 값을 잃지 않습니다. 다음 예를 고려하십시오.

예제 #4 정적 변수의 필요성 입증

기능 검사()
{
$a = 0;
에코 $a ;
$a++;
}
?>

이 함수는 호출될 때마다 $a를 다음과 같이 설정하므로 꽤 쓸모가 없습니다. 0 그리고 출력 0 . $a ++ 변수의 증가는 함수가 종료되면 $a 변수가 사라지기 때문에 여기서는 역할을 하지 않습니다. 현재 카운터 값을 잃지 않는 유용한 계산 함수를 작성하려면 변수 $a를 정적으로 선언합니다.

예 #5 정적 변수 사용 예

기능 검사()
{
정적 $a = 0 ;
에코 $a ;
$a++;
}
?>

이제 $a는 첫 번째 함수 호출에서만 초기화되며, 각 함수 호출 시험()$a의 값을 인쇄하고 증가시킵니다.

정적 변수를 사용하면 재귀 함수로 작업할 수도 있습니다. 재귀 함수는 자기 자신을 호출하는 함수입니다. 재귀 함수를 작성할 때는 재귀를 무한하게 만들 가능성이 있으므로 주의해야 합니다. 재귀를 종료할 적절한 방법이 있는지 확인해야 합니다. 다음의 간단한 함수는 정지 시점을 결정하기 위해 정적 변수 $count를 사용하여 최대 10까지 재귀적으로 계산합니다.

논평:

이전 예제와 같이 정적 변수를 선언할 수 있습니다. 표현식의 결과인 이러한 변수에 값을 할당하려고 하면 처리 오류가 발생합니다.

예제 #7 정적 변수 선언

함수 foo()(
정적 $int = 0 ; // 오른쪽
정적 $int = 1 + 2 ; // 틀렸습니다(표현식이므로)
정적 $int = sqrt(121); // 틀렸습니다(이것도 표현식이기 때문에)

$int++;
에코 $int ;
}
?>

논평:

정적 선언은 스크립트 컴파일 중에 평가됩니다.

글로벌( 글로벌) 및 정적( 공전) 변수

PHP 4를 구동하는 Zend Engine 1은 정적 및 전역 변수 수정자를 참조로 처리합니다. 예를 들어, 키워드를 지정하여 함수 범위에 포함된 실제 전역 변수 글로벌, 실제로 전역 변수에 대한 참조를 생성합니다. 이로 인해 다음 예와 같이 예기치 않은 동작이 발생할 수 있습니다.

함수 test_global_ref() (
전역 $obj ;
$obj = &새 표준클래스 ;
}

함수 test_global_noref() (
전역 $obj ;
$obj = 새로운 표준클래스;
}

test_global_ref();
var_dump($obj);
test_global_noref();
var_dump($obj);
?>

이 예제를 실행한 결과: get_instance_noref () (
정적 $obj ;

에코 "정적 개체: ";
var_dump($obj);
if (!isset($obj )) (
// 정적 변수에 객체 할당
$obj = 새로운 표준클래스;
}
$obj -> 속성++;
$obj를 반환합니다;
}

$obj1 = get_instance_ref();
$still_obj1 = get_instance_ref();
에코 "\n" ;
$obj2 = get_instance_noref();
$still_obj2 = get_instance_noref();
?>

이 예제를 실행한 결과는 다음과 같습니다.

정적 개체: NULL
정적 개체: NULL

정적 개체: NULL
정적 객체: object(stdClass)(1) (
["속성"]=>
정수(1)
}

이 예는 정적 변수에 참조를 할당할 때 참조를 할당하지 않음을 보여줍니다. 기억에 남는함수를 호출할 때 &get_instance_ref()두 번째.

다양한 기능을 갖춘 본격적인 웹사이트를 만들려면 많은 것을 알아야 합니다. 그러나 PHP는 사이트에 진정한 고유성을 부여할 수 있습니다. 전역 변수는 이 프로그래밍 언어에서 자주 사용되지 않지만 때로는 작동 방식을 아는 것이 매우 유용합니다.


이번 글에서는 전역변수가 무엇인지, 그리고 어떻게 작동하는지를 정확하게 공부하겠습니다.

전역 변수: 범위

변수가 정의되는 컨텍스트를 해당 범위라고 합니다. 일반적으로 변수에는 범위가 하나만 있습니다. PHP의 전역 변수가 다른 파일에서 로드되면 필수이거나 포함될 수 있습니다. 기본적으로 함수의 로컬 범위로 제한됩니다. 변수를 경계 너머의 파일에 표시하고 사용할 수 있게 하려면 어떻게 해야 합니까? 이것이 바로 PHP가 전역 변수를 제공하는 이유입니다. 여기서 핵심 단어는 "글로벌"입니다. PHP에서 전역 변수를 선언하는 방법은 무엇입니까? 이 목표를 달성하려면 "글로벌"이라는 단어를 사용해야 합니다. 전역으로 만들려는 변수 바로 앞에 배치해야 합니다. 이는 다음과 같습니다: 전역 "변수". 이러한 종류의 지침을 구현한 후에는 모든 파일에서 데이터 작업을 수행할 수 있습니다.

이 변수에 대한 참조가 어딘가에 있으면 프로그램은 전역 버전에 주의를 기울일 것입니다. 왜 그런 이상한 표현이 사용됩니까? 문제는 동시에 로컬 버전도 존재할 수 있다는 것입니다. 그러나 선언된 파일에서만 더 쉽게 액세스할 수 있습니다. 나머지에는 전역 PHP 클래스 변수가 적용됩니다. 여기서는 매우 신중하고 신중하게 행동해야 합니다. 의심을 방지하기 위해 어떻게 보일지에 대한 간단한 예를 들어 보겠습니다. 전역 a. 하나의 파일이 여러 변수에 액세스할 수 있으면 충돌이 발생할 수 있습니다. 하지만 여기서 전역 변수를 읽을지, 지역 변수를 읽을지, 오류가 발생할지 확실하게 말할 수는 없습니다. 함수 안에 작성하면 문제가 발생하지 않습니다. 함수 경계 밖에서 변수를 사용하는 것은 문제가 됩니다. 따라서 코드 구조를 매우 주의 깊게 모니터링하고 충돌에 대한 전제 조건이 없는지 확인해야 합니다.

전역 변수: 또 다른 표기법
전역 변수를 설정하는 다른 방법이 있습니까? 예, 혼자가 아닙니다. 먼저 $GLOBALS를 살펴보겠습니다. 키가 이름인 연관 배열입니다. 전역 변수의 내용이 값으로 사용됩니다. 선언 후에는 이 배열이 모든 범위에 존재한다는 점은 주목할 가치가 있습니다. 이는 슈퍼글로벌이라고 생각할 수 있는 근거를 제공합니다. $GLOBALS ['변수']와 같습니다.

슈퍼글로벌
모든 프로그래밍 언어에는 개별 기능을 위해 예약된 이름이 있습니다. PHP에서는 같은 이름의 전역 변수를 만드는 것이 불가능합니다. 이 프로그래밍 언어에는 고유한 특성이 있습니다. 예를 들어, 미리 정의된 변수에는 "super"라는 접두사가 없는 것이 특히 중요합니다. 즉, 모든 위치에서 사용할 수는 없습니다. 이 상황을 어떻게 바로잡을 수 있습니까? 일부 로컬 네트워크에서 미리 정의된 변수를 사용할 수 있도록 하려면 전역 "변수"와 같이 선언해야 합니다. 이것은 이미 앞에서 언급되었습니다. 그러나 이것은 전적으로 사실이 아닙니다. 실제 예를 살펴보겠습니다.
글로벌 $HTTP_POST_VARS; 에코 $HTTP_POST_VARS ['이름'].
차이점을 느끼시나요? PHP에서는 전역 변수가 함수 내에서 사용되어야 한다는 점을 명심할 가치가 있습니다. 또한 해당 파일에 포함된 파일에 있을 수도 있습니다.

보안 및 링크
직접 볼 수 있듯이 PHP에서 전역 변수를 생성하는 것은 문제가 되지 않습니다. 그런데 링크와 관련된 구체적인 내용이 있나요? 전역 변수를 사용할 때 예상치 못한 동작이 발생할 수 있습니다. 하지만 이 문제를 더 자세히 연구하기 전에 먼저 배경을 살펴볼 필요가 있습니다. 버전 4.2에서는 Register_globals 지시어가 기본적으로 활성화에서 비활성화로 변경되었습니다. 많은 사용자에게 이것은 완전히 중요하지 않으며 헛된 일입니다. 왜냐하면 개발 중인 제품의 안전성이 이에 직접적으로 달려 있기 때문입니다. 전역 변수를 만들어야 하는 경우 PHP 지시어는 이 설정에 직접적인 영향을 미치지 않습니다. 그러나 잘못된 사용은 보안 위험이 될 수 있습니다. 예를 들어, Register_globals가 활성화된 상태라면 코드가 실행되기 전에 필요한 다양한 변수가 초기화됩니다. 따라서 그들은 그것을 끄기로 결정했습니다. 전역 변수의 상태 중 많은 부분이 주어진 지시문에 의존하는 이유는 무엇입니까? 문제는 활성화했을 때 개발자가 그것이 어디서 왔는지에 대한 질문에 항상 대답할 수는 없었지만, 반면에 이는 코드 작성 프로세스를 크게 촉진했다는 것입니다. 동시에 그러한 조직은 보안에 특정 위협을가했습니다. 데이터 혼합 및 오류를 방지하기 위해 지시어가 비활성화되었습니다. 이제 안전하지 않은 코드의 예를 살펴보겠습니다. 또한, PHP 전역 변수 선언 시 정보 교체 시도가 동반되는 경우를 감지하는 방법도 살펴보겠습니다. 이는 처음 접하는 사용자가 해킹할 수 없는 안정적인 작업 사이트를 만들기 위해 필요합니다.

위험한 코드
권한이 부여된 사용자에 대해 변수를 true로 설정해 보겠습니다.
If (authenticate_user()) ($authoriza=true;) if ($authorize) (include "/highly/sensitive/data.php";). 이 상태의 변수는 자동으로 설정될 수 있습니다. 데이터를 간단히 교체할 수 있고 원본 소스가 확립되지 않았다는 점을 고려하면 사실상 모든 사용자가 이러한 검사를 통과하고 다른 사람을 사칭할 수 있습니다. 공격자는 원하는 경우 전체 스크립트의 논리를 방해할 수 있습니다. 지시문의 값을 변경하면 코드가 올바르게 작동합니다. 이것이 바로 우리가 해야 할 일입니다. 그러나 변수 초기화는 프로그래머들 사이에서 좋은 습관일 뿐만 아니라 스크립트의 안정성도 보장합니다.

믿을 수 있는 옵션
이 목표를 달성하려면 지시문을 비활성화하거나 다음과 같이 더 복잡한 코드를 작성할 수 있습니다. if (isset($_SESSION ['username'])) (echo “Hello” ($_SESSION ['username' ])”;) else (“Hello Guest”를 에코하고 “환영합니다!”를 에코합니다;). 이 경우 교체가 어렵습니다. 그러나 가능합니다. 이를 위해서는 신속한 대응 도구의 가용성을 미리 관리해야 합니다. PHP에 전역 변수를 포함해야 하는 경우 다음 도구를 사용할 수 있습니다. 값이 수신될 범위를 정확히 알고 있는 경우 스크립트가 이 사실을 비교하여 확인하는 방식으로 작성할 수 있습니다. 물론 이는 가치 대체에 대한 100% 보호를 보장할 수 없습니다. 그러나 가능한 옵션을 선택하면 작업이 상당히 복잡해집니다.

스푸핑 시도를 감지하는 방법은 무엇입니까?
이제 이전에 작성된 모든 내용을 올바르게 이해했는지 확인해 보겠습니다. 함수에서 전역 변수를 직접 선언해야 합니다. 이것은 일종의 숙제입니다. 먼저 코드는 다음과 같습니다.

몇 가지 설명을 해보자. C_COOKIE 변수는 신뢰할 수 있는 소스에서 가져옵니다. 결과가 예상대로인지 확인하기 위해 변수 값을 확인합니다. 문제가 발생하면 관리자에게 알림이 전송됩니다. 아무 일도 일어나지 않으면 아무 조치도 취하지 않습니다.