2017-03-23 3 views
0

クラスに次のことを考えてみましょう:オーバーライドされた親メソッドに対するより厳密な型ヒント?

class objectCollection implements Iterator { 

    private $objectArray = []; 
    private $position = 0; 


    public function __construct() { 
     $this->position = 0; 
    } 

    public function add($object){ 
    if(!in_array($object, $this->objectArray)) 
     $this->objectArray[] = $object; 
    return $this; 
    } 

    public function remove($object){ 
    if(($key = array_search($object, $this->objectArray())) !== false) 
     unset($this->objectArray[$key]); 
    return $this; 
    } 

    public function rewind() { 
     $this->position = 0; 
    } 

    public function current() { 
     return $this->objectArray[$this->position]; 
    } 

    public function key() { 
     return $this->position; 
    } 

    public function next() { 
     ++$this->position; 
    } 

    public function valid() { 
     return isset($this->objectArray[$this->position]); 
    } 

} 

class attachmentCollection extends objectCollection { 

    public function add(attachment $attachment){ 
    return parent::add($attachment); 
    } 

    public function remove(attachment $attachment){ 
    return parent::remove($attachment); 
    } 

} 

これはfollwingエラーを生成しますattachmentCollectionの 宣言::追加は、()objectCollectionと互換性があります::($オブジェクト)を追加

をあなたが見てみるとコード、私はそれがむしろ明らかに私が何をしようとしていると思う。 attachmentCollectionは、objectCollectionと基本的に同じですが、追加(または削除)できるオブジェクトはattachmentのインスタンスである必要があります。

これを行う正しい方法は何ですか?

+0

限り私は知っている、PHPは、より高い言語によって行われるように同じ方法でオーバーロードをサポートしていない...それらは同じ署名を持っている必要があります... –

+0

ああ、大丈夫です。それは酷いことだ。 – minychillo

答えて

0

PHP errored code

PHP working code

誰もがよりよい解決策を持っていない場合は

public function add($object){ 
    if(!in_array($object, $this->objectArray)) 
     $this->objectArray[] = $object; 
    return $this; 
    } 


public function remove($object){ 
    if(($key = array_search($object, $this->objectArray())) !== false) 
     unset($this->objectArray[$key]); 
    return $this; 
    } 

この

public function add(attachment $object){ 
    if(!in_array($object, $this->objectArray)) 
     $this->objectArray[] = $object; 
    return $this; 
} 
public function remove(attachment $object){ 
    if(($key = array_search($object, $this->objectArray())) !== false) 
     unset($this->objectArray[$key]); 
    return $this; 
    } 
+0

あなたの答えをありがとう!もちろん、これはエラーを取り除きますが、私は別のタイプヒントを持つobjectCollectionから他のクラスを拡張することはできません。 たとえば 'add'メソッドが 'product'オブジェクトのみを受け入れる 'productCollection'のように – minychillo

+0

@minychillo 'strict_types'を使用している場合は、親クラスでもそれに従わなければなりません。 –

0

に変更これは、まだここに(私が一緒に行ったものに開かれていますより良い解決法):

あなたがオブジェクトクラスとメソッドから、さらにクラスを拡張したい場合は
class attachmentCollection extends objectCollection { 

    public function add($attachment){ 
    if(! $attachment instanceof attachment) throw new \Exception('Argument must be instance of attachment'); 
    return parent::add($attachment); 
    } 

    public function remove($attachment){ 
    if(! $attachment instanceof attachment) throw new \Exception('Argument must be instance of attachment'); 
    return parent::remove($attachment); 
    } 

} 
0

が適合するものでなければならない、それから私は、たとえば、渡されたパラメータとしてインターフェイスを使用することをお勧めします:

interface collection{  
    //your methods 
} 

class objectCollection implements Iterator { 

    private $objectArray = []; 
    private $position = 0; 

    public function add(collection $object){ 
     if(!in_array($object, $this->objectArray))      
     $this->objectArray[] = $object; 
     return $this; 
    } 

    public function remove(collection $object){ 
     if(($key = array_search($object, $this->objectArray())) !==false) 
     unset($this->objectArray[$key]); 
     return $this; 
    } 
    .... 
} 


class attachmentCollection extends objectCollection { 

    public function add(collection $attachment){ 
     return parent::add($attachment); 
    } 

    public function remove(collection $attachment){ 
     return parent::remove($attachment); 
    } 

} 

class productCollection extends objectCollection { 

    public function add(collection $attachment){ 
     return parent::add($attachment); 
    } 

    public function remove(collection $attachment){ 
     return parent::remove($attachment); 
    } 

} 


class attachment implements collection { 
    //implement interface methods 
} 

class product implements collection{ 
    //implement interface methods 
} 
関連する問題