Question about overriding a class method

Hey there, long time procedural programmer attempting to make the jump to OOP. I’m currently reading SitePoint’s PHP Anthology 101 Tips book and have a question about something I’ve read.

In the first chapter they describe how you can override / modify a parent method in a child but at the same time you can also refer back to the parent method to get some results. Here’s an example from the code archive.

The parent class:


<?php
class HTMLElement
{
  protected $content;
  protected $tagname;
  protected $attributes;
  
  public function __construct($content, $attributes = array())
  {
    $this->content = $content;
    $this->attributes = $attributes;
  }
   
  public function getSource()
  {
    return '<' . $this->tagname . $this->getAttributeSource() . '>' .
        $this->content . 
        '</' . $this->tagname . '>';
  }
  
  public function getAttributeSource()
  {
    $attributes = '';  
    if (count($this->attributes)) {
      foreach ($this->attributes as $attrnme => $attrval)
      {
        $attributes .= ' ' . $attrnme . '="' . $attrval . '"';
      }
    }
    return $attributes;
  }
  
  public function __toString()
  {
    return $this->getSource();
  }
}

?>

And the child class that extends the htmlElement class:


<?php
require_once 'HTMLElement.class.php';

class HTMLImage extends HTMLElement
{
  protected $tagname = 'img';
  public function __construct($content, $attributes = array())
  {
    parent::__construct('', $attributes);
  }
  
  public function getSource()
  {
    return '<' . $this->tagname . $this->getAttributeSource() . ' />';
  }
  
  public function getAttributeSource()
  {
    if (!array_key_exists('alt',$this->attributes)) {
      $this->attributes['alt'] = 'This image needs alt text';
    }
    return parent::getAttributeSource();
  }
}
?>

Ok so here’s what’s not clear to me. In the following code the child class manipulates the values going into the attributes array like so:


public function getAttributeSource()
  {
    if (!array_key_exists('alt',$this->attributes)) {
      $this->attributes['alt'] = 'This image needs alt text';
    }
    return parent::getAttributeSource();
  }

Should I assume that the getAttributeSource method in the child class is run after the parent class? Because looking at the code from a procedural standpoint, if the child class puts something in attributes then goes and runs the same method in the parent class, the first line in the parent classes getAttributeSource method is:


$attributes = "";

Would I not just empty the variable in the child class I created?

I hope that makes sense, perhaps I’m still thinking too procedurally but I’m trying to sort out what get run in which order.

Thanks!

$attributes is not the same as $this->attributes. $attributes is a completely separate variable restricted to the scope of the method HTMLElement::getAttributeSource(). Where as $this->attributes is a object property accessible to all methods and maintaining state throughout the duration of the objects existence.

Therefore, the HTML element merely loops through the entire attribute array building a attribute value string. The method which overrides it in the image class makes sure a alt attribute always exists. If an alt attribute doesn’t exists than it adds a placeholder with default text. At which point the parent method is called and the output string is generated containing the alt text.

Ahhh right! I hadn’t even considered scope. Thanks :slight_smile: