phpclass/클래스활용2000. 7. 13. 14:07
__sleep, __wakeup과 같이 "__"로 시작하는 매직함수(magic function)는 PHP 클래스 내에서 특수한 목적으로 사용됩니다. 따라서 이 함수들이 가지고 있는 문서화된 매직 기능을 사용할 필요가 없다면 클래스 내에 이 함수들을 정의해서는 안됩니다.
__sleep
serialize 함수를 통해 객체를 직렬화할 때 해당 클래스에 매직 함수 __sleep가 정의되어 있는지 확인합니다. 만약 정의되어 있다면 객체를 직렬화하기 전에 __sleep 함수를 수행합니다. 이 함수는 직렬화하기 전에 객체 멤버에 대하여 조작해야 하는 작업, 또는 직렬화하기 전에 미리 수행해야 하는 작업(예를 들어 데이터베이스 연결 종료 등)을 수행할 수 있습니다. __sleep 함수는 직렬화할 객체의 모든 멤버변수의 이름을 변수에 담아 반환합니다.
[code php;gutter:false] class Scott {
var $error;
var $svar = array();

function Scott() {
$this->svar['Hello'] = "World";
}

function __sleep() {
$this->svar['Hello'] = "Yawn";
// return list of instance-variables to be serialized
return array('error', 'svar');
}
}

$x = new Scott();
print_r($x);
$y = serialize($x);
$z = unserialize($y);
print_r($z); [/code]
__wakeup
unserialize 함수를 통해 문자열을 객체화할 때 해당 클래스에 매직 함수 __wakeup가 정의되어 있는지 확인합니다. 만약 정의되어 있다면 객체화하기 전에 __wakeup 함수를 수행합니다. 이 함수를 수행할 때 객체화하기 전에 객체를 상대로 수행해야하는 작업, 또는 객체화하기 전에 미리 수행해야 하는 작업(예를 들어 데이터베이스 연결 등)을 수행할 수 있습니다.
[code php;gutter:false] class Scott {
var $error;
var $svar = array();

function Scott() {
$this->svar['Hello'] = "World";
}

function __sleep() {
$this->svar['Hello'] = "Yawn";
// return list of instance-variables to be serialized
return array('error', 'svar');
}

function __wakeup() {
$this->svar['test'] = "I'm here!";
}
}

$x = new Scott();
print_r($x);
$y = serialize($x);
$z = unserialize($y);
print_r($z); [/code]

Posted by 방글24
phpclass/클래스활용2000. 7. 13. 14:05
부모클래스의 메소드 호출
보통 부모클래스에서 선언된 메소드를 자식클래스에서 재정의하는 이유는 크게 두가지가 있습니다.
1. 부모클래스 메소드를 완전히 새롭게 정의하기 위하여
2. 부모클래스 메소드의 기능에 새로운 기능을 추가하기 위하여
첫 번째 기능은 부모클래스의 메소드를 무시하고 메소드에 새로운 정의를 함으로써 부모클래스의 메소드 정의를 숨기는 것입니다. 그러나 때로는 부모클래스의 메소드를 모두 지우는 것보다는 추가적인 기능이 필요한 경우가 있습니다. 이같은 경우에는 부모클래스의 메소드와 자식클래스에서 재정의된 메소드를 모두 수행하게 될 것입니다. 즉, 재정의된 메소드 구문 내에서 부모클래스의 메소드를 호출할 수 있어야 하며 필요한 기능만 추가적으로 작성하면 될 것입니다. 이럴 때 부모클래스의 메소드를 호출하기 위해서 사용하는 키워드가 parent입니다. 자바에서의 키워드 super와 같은 역할을 하며 이것은 그 메소드 호출을 상위클래스로 전달합니다.
부모키워드 parent는 $this 키워드와 비슷하게 이 클래스의 부모클래스를 나타내는 위치 지정자입니다. 현재 클래스의 부모클래스를 참조해야 되는 경우에는 부모키워드 parent를 사용할 수 있습니다.
[code php;gutter:false] class A {
function example() {
echo "클래스 A에 정의된 메소드 example. \n";
}
}

class B extends A {
function example() {
echo "클래스 B에서 재정의된 메소드 example. \n";
parent::example();
}
}

$b = new B;

$b->example(); [/code]
이 예의 출력결과를 보면 아래와 같이 나타날 것입니다.
클래스 B에서 재정의된 메소드 example.
클래스 A에 정의된 메소드 example.
앞장 범위연산자에서 설명한 대로 키워드 parent 대신에 extends 다음에 기술된 부모클래스명을 직접 사용해도 됩니다.
parent::example();  ------>  A::example();
키워드 parent를 써야 될 이유
위의 예에서 부모클래스를 A가 아닌 A1으로부터 상속받도록 수정하여야 한다면 아래와 같이 extends 다음에 있는 부모클래스명을 변경하는 것으로 모든 작업은 끝나게 됩니다. 만약 parent::example()가 아닌 A::example()라고 작성하였었다면 이 부분도 A1::example()라고 수정하여야 할 것입니다. 결국 수정할 때 손이 더 많이 가야 하는 것이지요. 그러니 부모클래스에 있는 메소드에 접근하는 경우라면 키워드 parent를 이용하는 것이 소스 코드를 관리하는데 훨씬 유리할 것입니다.
[code php;gutter:false] class B extends A1 {
function example() {
echo "클래스 B에서 재정의된 메소드 example. \n";
parent::example();
}
}

$b = new B;

$b->example(); [/code]

Posted by 방글24
phpclass/클래스활용2000. 7. 13. 14:04
범위연산자란?
PHP4에서만 지원되며 클래스와 메소드 또는 클래스와 멤버변수를 연결시켜 주는 일로 범위연산자(scope resolver) 뒤에 나오는 메소드와 멤버변수의 스코프(사용범위)를 지정하는 일을 하는 것입니다.
클래스명::메소드명
클래스명::멤버변수명
범위연산자 사용목적
1. 인스턴스되지 않은 클래스의 메소드에 접근할 때
2. 부모클래스의 메소드와 멤버변수에 접근할 때
인스턴스되지 않은 클래스에 있는 메소드에 접근할 때
[code php;gutter:false] class A {
function example() {
echo "클래스 A에 정의된 메소드 example. \n";
}
}

A::example(); [/code]
아직 클래스 A에 대한 객체가 생성되기 전이지만 범위연산자를 이용하면 일반 함수처럼 실행시킬 수 있습니다. 그러나 클래스 A에 대한 객체가 전혀 생성되어 있지 않으므로 클래스 외부에서 이 함수에 접근할 때는 이 함수 내에 $this 객체를 사용해서는 안됩니다. 물론 일반 함수와 마찬가지로 지역 변수 및 전역 변수를 사용할 수는 있습니다.
[code php;gutter:false] class A {
var $var = "초기값";

function example() {
echo "클래스 A에 속한 메소드 example. \n";
echo $this->var . "\n";
}
}

A::example(); [/code]
위의 예제를 보면 아직 클래스 A에 대한 객체가 생성되지 않았으므로 멤버변수 $var에 대한 기억장소가 할당되지도 않았고 더구나 초기값을 설정할 수도 없습니다. 그러니 아무리 범위연산자를 이용하여 메소드 example()에 접근한다해도 멤버변수 $var의 초기값을 나타낼 수는 없을 것입니다. 실험해 본 바로는 이 경우 $this->var의 값이 NULL로 처리되는 것 같습니다.
부모클래스의 메소드에 접근할 때
[code php;gutter:false] class A {
function example() {
echo "클래스 A에 정의된 메소드 example. \n";
}
}

class B extends A {
function example() {
echo "클래스 B에서 재정의된 메소드 example. \n";
A::example();
}
}

$b = new B;

$b->example(); [/code]
이 예의 출력결과를 보면 아래와 같이 나타날 것입니다.
클래스 B에서 재정의된 메소드 example.
클래스 A에 정의된 메소드 example.
범위연산자는 클래스가 상속되었을 때 재정의되기 전의 부모클래스에 있는 메소드에 접근할 때 유용하게 사용될 수 있습니다.
부모클래스의 멤버변수에 접근할 때
php.net의 문서 설명과는 달리 아직 공개되지 않는 어떤 방법이 있는 지는 모르겠으나 부모클래스의 멤버변수로 접근하는 방법에 대하여는 문서화되지 않은 것 같습니다.

Posted by 방글24