2011-01-26 93 views
1

任何人都知道在PHP中是否有可能強制一個類擴展或實現一個接口而不需要聲明它的子類?強制一個動態加載的類來擴展或實現一個接口

例子:

interface Requirements 
{ 
    public function __construct(); 
    public function kittens(); 
} 

class DingleBerry 
{ 
    public function __construct() 
    { 
     // yadda yadda yadda  
    } 
} 

// Example of my initial hope 
// of what you could do 

$kittens = new DingleBerry implements Requirements; 

顯然,這是不行的,但我需要裝載在具有的接口的要求沒有預定的知識,但被迫遵守他們班的方式。

我的總體目標是檢查該類是否實現了它的加載並調用其構造函數的要求BEFORE

,所以我不能用這個:

interface Requirements 
{ 
    public function __construct(); 
    public function kittens(); 
} 

class DingleBerry 
{ 
    public function __construct() 
    { 
     // DO BAD STUFF (i.e. eat your soul) 
    } 
} 

// Example of what I CANNOT 
// do. 

$kittens = new DingleBerry; 

if(!($kittens instanceof Requirements)) 
{ 
    // eat pizza.  
} 

因爲那時DingleBerry的構造函數被調用之前,我可以檢查它是否實現了要求。挖?

回答

1

未經測試,但理論上是這樣的API:

<?php 
$reflection = new ReflectionClass('DingleBerry'); 
$reflection->implementsInterface('Requirements'); 
?> 

http://php.net/manual/en/book.reflection.php
http://mark-story.com/posts/view/using-the-php-reflection-api-for-fun-and-profit

+0

這將** **檢查,如果該接口實現,但不會讓班級執行它。 – netcoder 2011-01-26 23:53:44

+0

嗯,那就是你的問題的第二部分,關於在調用DingleBerry的構造函數之前,你可以檢查它是否實現了它。 – scragz 2011-01-26 23:56:14

1

,而無需使用第三方擴展(例如:runkit)您不能修改一個已經聲明的類或接口的定義。

Runkit具有可滿足該需求的runkit_class_adopt函數。不幸的是我無法測試它,因爲PECL版本無法在我的機器上編譯。

對於你的問題的第一部分,你可以檢查,如果一個類實現給定的接口沒有實例它,不反射API:

// checks if class Bar implements Foo 
if (in_array('Foo', class_implements('Bar'))) { 
    $foo = new Bar; 
} else { 
    throw new Exception('Interface not implemented'); 
} 
相關問題