PHP: 부모 클래스에서 자식 클래스의 함수를 호출하는 방법
부모 클래스에서 자녀 클래스의 함수를 어떻게 불러야 하나요?다음 사항을 고려하십시오.
class whale
{
function __construct()
{
// some code here
}
function myfunc()
{
// how do i call the "test" function of fish class here??
}
}
class fish extends whale
{
function __construct()
{
parent::construct();
}
function test()
{
echo "So you managed to call me !!";
}
}
그래서 추상 수업이 있는 거야.추상 클래스는 기본적으로 다음과 같습니다.나에게서 상속받는 사람은 모두 이 기능을 가지고 있어야 합니다.
abstract class whale
{
function __construct()
{
// some code here
}
function myfunc()
{
$this->test();
}
abstract function test();
}
class fish extends whale
{
function __construct()
{
parent::__construct();
}
function test()
{
echo "So you managed to call me !!";
}
}
$fish = new fish();
$fish->test();
$fish->myfunc();
좋아, 이 대답은 매우 늦었지만, 왜 아무도 이 생각을 하지 못했을까?
Class A{
function call_child_method(){
if(method_exists($this, 'child_method')){
$this->child_method();
}
}
}
이 메서드는 확장 클래스에서 정의됩니다.
Class B extends A{
function child_method(){
echo 'I am the child method!';
}
}
그래서 다음 코드와 함께:
$test = new B();
$test->call_child_method();
출력은 다음과 같습니다.
I am a child method!
자녀 클래스로 정의할 수 있지만 반드시 정의할 필요는 없는 콜 후크 메서드에 사용합니다.
엄밀히 말하면 고래 인스턴스(부모)에서 물고기 인스턴스(자녀)를 호출할 수 없지만 상속을 취급하고 있기 때문에 myFunc()는 물고기 인스턴스에서 사용할 수 있으므로 호출할 수 있습니다.$yourFishInstance->myFunc()
직접적으로.
템플릿 메서드 패턴을 참조하는 경우, 다음과 같이 적습니다.$this->test()
방법 주체로 사용합니다.부르기myFunc()
어류 인스턴스에서 호출을 위임합니다.test()
어류 인스턴스에서는요.하지만 고래 인스턴스에서 물고기 인스턴스로의 호출은 없습니다.
옆구리에서 고래는 포유동물이지 물고기가 아니다.
PHP 5.3에서는 static 키워드를 사용하여 호출된 클래스에서 메서드를 호출할 수 있습니다.
<?php
class A {
public static function who() {
echo __CLASS__;
}
public static function test() {
static::who(); // Here comes Late Static Bindings
}
}
class B extends A {
public static function who() {
echo __CLASS__;
}
}
B::test();
?>
위의 예는 다음과 같습니다.b
출처: PHP.net / 레이트 스태틱바인딩
좋아요, 이 질문에는 잘못된 점이 너무 많아서 어디서부터 시작해야 할지 모르겠어요.
첫째, 물고기는 고래가 아니고 고래는 물고기가 아니다.고래는 포유동물이다.
둘째, 부모 클래스에 존재하지 않는 부모 클래스의 함수를 호출하려면 추상화에 심각한 결함이 있으므로 처음부터 다시 생각해야 합니다.
셋째, PHP에서는 다음 작업을 수행할 수 있습니다.
function myfunc() {
$this->test();
}
의 경우whale
에러의 원인이 됩니다.의 경우fish
그건 작동할 거야.
저는 추상 수업을 듣겠습니다.
그러나 PHP에서는 동작시키기 위해 그것들을 사용할 필요가 없습니다.부모 클래스의 컨스트럭터 호출도 "정상" 메서드 호출이며, 이 시점에서 오브젝트는 완전히 "작동 가능"합니다.즉, $this this "know"는 상속 여부에 관계없이 모든 멤버에 대해 "알고 있습니다.
class Foo
{
public function __construct() {
echo "Foo::__construct()\n";
$this->init();
}
}
class Bar extends Foo
{
public function __construct() {
echo "Bar::__construct()\n";
parent::__construct();
}
public function init() {
echo "Bar::init()\n";
}
}
$b = new Bar;
인쇄하다
Bar::__construct()
Foo::__construct()
Bar::init()
즉, 클래스 Foo는 함수 init()에 대해 아무것도 모르더라도 참조하는 $에 따라 검색이 이루어지기 때문에 메서드를 호출할 수 있습니다.
그건 기술적인 측면이에요.그러나 추상화(하위에게 강제 구현)하거나 덮어쓸 수 있는 기본 구현을 제공하여 이 메서드의 구현을 실제로 수행해야 합니다.
당신에게는 조금 늦은 감이 있지만, 저도 이 문제를 해결해야 했습니다.이것이 필요한 이유를 다른 사람이 이해할 수 있도록 하기 위해 예를 다음에 제시하겠습니다.
애플리케이션용 MVC 프레임워크를 구축하고 있습니다.기본 컨트롤러 클래스는 각 컨트롤러 클래스에 의해 확장됩니다.컨트롤러의 동작에 따라 컨트롤러마다 방법이 다릅니다.예를 들어 mysite.com/event은 이벤트 컨트롤러를 로드하고 mysite.com/event/create은 이벤트 컨트롤러를 로드하고 '생성' 메서드를 호출합니다.작성 함수의 호출을 표준화하려면 기본 컨트롤러 클래스가 자녀 클래스의 메서드에 액세스해야 합니다.자 클래스의 메서드는 컨트롤러마다 다릅니다.코드적으로는 부모 클래스가 있습니다.
class controller {
protected $aRequestBits;
public function __construct($urlSegments) {
array_shift($urlSegments);
$this->urlSegments = $urlSegments;
}
public function RunAction($child) {
$FunctionToRun = $this->urlSegments[0];
if(method_exists($child,$FunctionToRun)) {
$child->$FunctionToRun();
}
}
}
다음으로 자녀 클래스:
class wordcontroller extends controller {
public function add() {
echo "Inside Add";
}
public function edit() {
echo "Inside Edit";
}
public function delete() {
echo "Inside Delete";
}
}
따라서 이 경우 해결책은 자식 인스턴스 자체를 부모 클래스에 매개 변수로 전달하는 것이었습니다.
네가 이걸 할 수 있는 유일한 방법은 성찰하는 거야.그러나 반사는 비용이 많이 들기 때문에 필요할 때만 사용해야 합니다.
여기서 진짜 문제는 부모 클래스가 자녀 클래스 메서드의 존재에 의존해서는 안 된다는 것입니다.이것은 OOD의 지침으로, 당신의 디자인에 심각한 결함이 있음을 나타냅니다.
부모 클래스가 특정 자식 클래스에 종속되어 있는 경우 부모 클래스를 확장할 수 있는 다른 자식 클래스에서도 사용할 수 없습니다.부모-자녀 관계는 추상화에서 구체성으로, 그 반대는 아니다.대신 필요한 함수를 부모 클래스에 배치하고 필요에 따라 자녀 클래스에서 덮어쓰는 것이 훨씬 좋습니다.다음과 같은 경우:
class whale
{
function myfunc()
{
echo "I am a ".get_class($this);
}
}
class fish extends whale
{
function myfunc()
{
echo "I am always a fish.";
}
}
아주 간단해요.추상 수업 없이 이 작업을 수행할 수 있습니다.
class whale
{
function __construct()
{
// some code here
}
/*
Child overridden this function, so child function will get called by parent.
I'm using this kind of techniques and working perfectly.
*/
function test(){
return "";
}
function myfunc()
{
$this->test();
}
}
class fish extends whale
{
function __construct()
{
parent::construct();
}
function test()
{
echo "So you managed to call me !!";
}
}
오래된 질문이라도 Reflection Method를 사용한 솔루션:
class whale
{
function __construct()
{
// some code here
}
function myfunc()
{
//Get the class name
$name = get_called_class();
//Create a ReflectionMethod using the class and method name
$reflection = new \ReflectionMethod($class, 'test');
//Call the method
$reflection->invoke($this);
}
}
ReflectionMethod 클래스를 사용하면 일련의 인수를 전달하고 호출하는 메서드에 필요한 인수를 확인할 수 있습니다.
//Pass a list of arguments as an associative array
function myfunc($arguments){
//Get the class name
$name = get_called_class();
//Create a ReflectionMethod using the class and method name
$reflection = new \ReflectionMethod($class, 'test');
//Get a list of parameters
$parameters = $reflection->getParameters()
//Prepare argument list
$list = array();
foreach($parameters as $param){
//Get the argument name
$name = $param->getName();
if(!array_key_exists($name, $arguments) && !$param->isOptional())
throw new \BadMethodCallException(sprintf('Missing parameter %s in method %s::%s!', $name, $class, $method));
//Set parameter
$list[$name] = $arguments[$name];
}
//Call the method
$reflection->invokeArgs($this, $list);
}
고래 인스턴스에서는 이 함수를 호출할 수 없습니다.하지만 물고기 인스턴스에서는
function myfunc()
{
static::test();
}
자 클래스에 메서드가 있는 경우 부모 클래스에서 메서드가 호출됩니다(존재하는 경우 옵션콜백으로 사용).
<?php
class controller
{
public function saveChanges($data)
{
//save changes code
// Insert, update ... after ... check if exists callback
if (method_exists($this, 'saveChangesCallback')) {
$arguments = array('data' => $data);
call_user_func_array(array($this, 'saveChangesCallback'), $arguments);
}
}
}
class mycontroller extends controller
{
public function setData($data)
{
// Call parent::saveChanges
$this->saveChanges($data);
}
public function saveChangesCallback($data)
{
//after parent::saveChanges call, this function will be called if exists on this child
// This will show data and all methods called by chronological order:
var_dump($data);
echo "<br><br><b>Steps:</b><pre>";
print_r(array_reverse(debug_backtrace()));
echo "</pre>";
}
}
$mycontroller = new mycontroller();
$mycontroller->setData(array('code' => 1, 'description' => 'Example'));
불가능한 OOP 개념에 대해 이야기하면 조금 까다롭습니다.
하지만 뇌를 사용하면 다음과 같이 될 수 있습니다:)
OOP는 부모 클래스에서 자식 클래스 함수를 호출할 수 없으며 상속은 자식에서 부모 함수를 상속하는 것으로 이루어지므로 정답입니다.
그렇지만
Static 클래스로 이 작업을 수행할 수 있습니다.
class Parent
{
static function test()
{
HelperThread::$tempClass::useMe();
}
}
class child extends parent
{
// you need to call this. functon everytime you want to use
static function init()
{
HelperThread::$tempClass = self::class;
}
static function useMe()
{
echo "Ahh. thank God you manage a way to use me";
}
}
class HelperThread
{
public static $tempClass;
}
그건 내 문제를 해결하는 방법일 뿐이야그것이 너의 문제에 도움이 되길 바란다.
해피 코딩 :)
고래가 늘어나지 않으면요?그 함수 호출은 어떤 결과를 낳을까요?불행하게도 그것을 할 방법이 없다.
오, 그리고 물고기는 고래를 연장하나요?물고기는 물고기이고, 고래는 포유동물이다.
언급URL : https://stackoverflow.com/questions/1944827/php-how-to-call-function-of-a-child-class-from-parent-class
'programing' 카테고리의 다른 글
교리 쿼리에서 null 값을 필터로 지정하는 방법은 무엇입니까? (0) | 2022.09.08 |
---|---|
어떻게 CentOS7에 MySQL루트 계정 비밀 번호를 바꾸도록? (0) | 2022.09.08 |
워드 프레스는 루프 밖에 있는 페이지 ID다. (0) | 2022.09.08 |
MySQL에서 날짜 비교 (0) | 2022.09.08 |
Windows for Node.js 의존관계에서 Python 실행 (0) | 2022.09.08 |