2013-01-04 16 views
16

Mam cechę. Ze względu na kreatywność, nazwijmy tę cechę. Cecha:Cechy wskazujące na typ PHP

trait Trait{  
    static function treat($instance){  
     // treat that trait instance with care 
    } 
} 

Teraz mam również klasę, która korzysta z tej cechy, Użytkownik. Kiedy próbujesz zadzwonić podarować z chwilą użytkownika, wszystko działa. Ale chciałbym, aby wpisać-wskazówkę, że tylko instancje klas korzystających cecha powinna być podane jako argumenty, tak:

static function treat(Trait $instance){...} 

Niestety, choć powoduje to fatalnym strzałką, która mówi, że funkcja spodziewali instancję Cecha, ale przypadek Użytkownika został podany. Ten typ podpowiedzi typu doskonale sprawdza się w przypadku dziedziczenia i implementacji, ale jak mogę wpisać - wskazówkę do cechy?

+3

Nie możesz. [Podręcznik] (http://php.net/manual/en/language.oop5.typehinting.php) wyraźnie to mówi. 'Wskazówki typów nie mogą być używane z typami skalarnymi, takimi jak int lub string. Cechy nie są dozwolone. " – DaveRandom

+0

DaveRandom jest poprawny, musisz użyć instrukcji' use', aby zaimplementować cechy, ponieważ nie są tworzone instancjami. – phpisuber01

+1

@DaveRandom myślę, że to jest inny php 'wtf' patrz http://eval.in/5936 jeśli nie będzie traktowany jako klasa, dlaczego otrzymujesz' Błąd krytyczny: nie można redeclare klasy Hello' – Baba

Odpowiedz

11

Nie możesz, jak mówi DaveRandom. I nie powinieneś. Prawdopodobnie chcesz zaimplementować interfejs i typhint na tym. Następnie można zaimplementować ten interfejs za pomocą cechy.

+7

Muszę powiedzieć, że nie zgadzam się z tym. Myślę, że typowe cechy wskazujące będą bardzo przydatne. Cechy pozwalają na deklarowanie metod abstrakcyjnych, więc gdyby dozwolona była podpowiedź typu, byłyby one prawdopodobnie bardziej użyteczne niż interfejsy, ponieważ a) obsługują dziedziczenie wielokrotne (jak interfejsy) i b) wspierają implementację (jak klasy abstrakcyjne, które _ są_ typem- podpowiedź). Ponieważ PHP nie jest skompilowane, podpowiedź typu jest najlepszą częścią abstrakcji, więc cechy nie są tak przydatne, jak mogłyby być. – Rob

+7

@Rob, To by spowodowało problem z aliasingiem metod ('use myTrait {myMethod as newMethod;}') w przypadku kolizji. Powiedzmy, że mam klasę myClass z jedną metodą "myMethod" i cechą myTrait zapewnia jakąś funkcjonalność, którą chcę dodać do myClass. Mogę alias funkcji "myMethod" do czegoś innego (newMethod w moim przykładzie). Teraz osoba B patrzy na to i widzi, że używam funkcji myTass w myClass, on myśli, że może użyć myClass z inną typową klasą. Ale to nie jest prawda. W przypadku interfejsu byłbym zmuszony do zachowania intencji myMethod tak samo. – Veda

+2

Muszę przyznać, że nie wiedziałem o metodach aliasingu cech. Jednak po niektórych testach nie można uzyskać aliasów metod abstrakcyjnych, a ponieważ [D] (http://en.wikipedia.org/wiki/Dependency_inversion_principle) oznacza zależność od abstrakcji, osoba B nie powinna być zależna od implementacji cech, ale raczej ich abstrakcyjne metody, jak w interfejsie lub klasie abstrakcyjnej. – Rob