Re: [PHP] How do I handle covariant parameters and not fall foul of LSP.
[email protected] (Richard Quadling)
| Newsgroups | php.general |
|---|---|
| Message-ID | <CAKUjMCUXm2udzaiFtZU5JWGnM2_9a5YT2jtPi6m7MhtKvvtGtg@mail.gmail.com> |
On 13 February 2017 at 16:36, Stefan A. <[email protected]> wrote: > I know it might look like deflecting the issue but maybe this could work > > abstract class BaseRepo > { > protected function doProcessEntity(BaseEntity $entity){} > } > > class PersonRepo extends BaseRepo > { > public function processEntity(Person $entity) > { > $this->doProcessEntity($entity); > } > } > > On Mon, Feb 13, 2017 at 5:13 PM, Richard Quadling <[email protected]> > wrote: > >> Hi. >> >> I have an abstract base repo and an abstract base entity. Both provide >> functionality >> appropriate to all repos/entities. >> >> I extend these to allow a specific repo to handle a specific entity. >> But I can't >> declare the specific entity type hint in the specific repo as it is in >> conflict. >> >> I'm hitting my head against LSP, but wanting >> https://en.wikipedia.org/wiki/Covariance_and_contravariance_ >> (computer_science)#Contravariant_method_argument_type >> >> <?php >> >> abstract class BaseEntity{} >> >> abstract class BaseRepo >> { >> public function processEntity(BaseEntity $entity){} >> } >> >> class Person extends BaseEntity{} >> >> class PersonRepo extends BaseRepo >> { >> public function processEntity(Person $entity) >> { >> parent::processEntity($entity); >> } >> } >> >> $person = new Person; >> $personRepo = new PersonRepo; >> $personRepo->processEntity($person); >> >> >> Warning: Declaration of PersonRepo::processEntity(Person $entity) >> should be compatible >> with BaseRepo::processEntity(BaseEntity $entity) >> >> I know some people 'get' this. But for me, it really seems to make next >> to no >> sense at all. >> >> I have some base behaviour for all entities. I have a base repo that can >> work >> with that base entity, regardless of how that entity is extended. >> >> If the base type were not abstract, then I can see that I wouldn't >> substitute >> anything logically, but I'm using abstract base types. And if set theory >> is >> to be believed, then if B extends A, B is still an A. And so, where I can >> receive an A, I can receive a B. >> >> Obviously, I'm missing / lacking an understanding of LSP as it relates to >> my >> code. >> >> I'm happy to read more, but I'd appreciate some recommendations on what to >> read. >> >> Of course, if anyone can 'correct' my code such that a concrete repo >> works on >> concrete entities, but also allows for the base behaviour, then I'd be >> very >> grateful. >> >> Regards, >> >> Richard. >> > > That's what I'm having to do. Just seems really odd.