Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>To fix the Notice, simply change <code>foo()</code> in the Child to</p> <pre><code>public function foo($arg = null) { </code></pre> <p>As to the question "why does this not work":</p> <p>Visibility in PHP is strictly about runtime access. It doesn't affect how you can extend/compose/overload classes and methods. Loosening the visibility of a private method from a Supertype in a Subtype will add a separate method in the subtype with no access to the same named method in the supertype. However, PHP will assume a parent-child relationship for these. That didn't cause the Notice though. At least, not on it's own.</p> <p>The reason why you get the Notice, is that you are then also trying to change the method signature. Your <code>foo()</code> does no longer require <code>$arg</code> to be passed to it. When you assume a parent-child relationship between the methods, this is a problem because the <a href="http://en.wikipedia.org/wiki/Liskov_substitution_principle" rel="nofollow">Liskov Substitution Principle</a> states that <em>"if S is a subtype of T, then objects of type T may be replaced with objects of type S"</em> without breaking the program. In other words: if you have code that uses <code>Base</code>, you should be able to replace <code>Base</code> with <code>Child</code> and the program should still work as if it was using <code>Base</code>. </p> <p>Assume your <code>Base</code> also has a public method <code>bar()</code>. </p> <pre><code>class SomeClientUsingBase { public function doSomethingWithBase(Base $base) { $result = $base-&gt;bar(); // … </code></pre> <p>Now imagine <code>Child</code> changes <code>bar()</code> to require an argument. If you then pass <code>Child</code> for <code>Base</code> into the client, you will break the client, because the client calls <code>$base-&gt;bar();</code> without an argument. </p> <p>Obviously, you could change the client to pass an argument, but then the code really depends on how <code>Child</code> defined the method, so the Typehint is wrong. In fact, <code>Child</code> is not a <code>Base</code> then, because it doesn't behave like a <code>Base</code>. It's broken inheritance then.</p> <p>Now the funny thing is, if you remove that <code>$arg</code> from <code>foo()</code>, you are technically not violating LSP, because the client would still work. The Notice is wrong here. Calling <code>$base-&gt;foo(42)</code> in a client that previously used <code>Base</code> will still work with a <code>Child</code> because the <code>Child</code> can simply ignore the argument. But PHP wants you to make the argument optional then.</p> <p>Note that LSP also applies to what a method may return. PHP just doesn't include the return type in the signature, so you have take that into account yourself. Your methods have to return what the Supertype returned or something that is behaviorally equivalent.</p>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload