Showing posts with label overloading. Show all posts
Showing posts with label overloading. Show all posts

Thursday, June 4, 2009

"Overloading" in PHP5 and magic methods

PHP doesn't support constructor / methods overloading with the classical syntax !

"Overloading" in PHP5 is realized via the magic method
__call($functionName, $argumentsArray)

Dynamic creation of PROPERTIES
Let's consider a class X (without content) and one its instance
class X {}
$x = new X();

Now, If we try to read the inexistent property "m1" of the class, that is:
print $->m1;
we have
  • if the class X contains the definition of the method
    public function __get($name) { ... }
    this method will be invoked passing "m1" in the 1st argument (no errors or notice will be generated)
  • if the class doesn't contain that method, php will generate a notice (Undefined property)

"__get()" is a "magic method", that php invokes when we access a variabile of the class.
There are other magic methods for each class we create:
  • __set($name, $value) : called when we assign a value to a member
    $x->m1 = "val"; // equivalent to $x->__set("m1","val");
  • __isset($name): called when we call isset() //since php 5.1.0
    isset($x->m1); // equivalent to $x->__isset("m1");
  • __unset($name): called when we call unset() //since php 5.1.0
    unset($x->m1); // equivalent to $x->__unset("m1");
note: magic methods work with each visibility public/protected/private !
note: if we access to "m1" and the class X already contains a member called "m1":
  • if accessible: php accesses to the value of the existend member "m1"
  • if non accessible: php invoke __get()
Dynamic creation of METHODS
A similar feature is available for methods:
  • __call( string $name , array $arguments )
    $x->method1(1,"val"); // equivalent to $x->__call("method1", array(1, "val") );
  • __callStatic( string $name , array $arguments ) //since php 5.3.0
    $x::method2(2,"val2"); // equivalent to $x->__call("method1", array(1, "val") );


PHP5: inheritance and overriding

example of inheritance
figure -> rectangle -> square figure -> triangle

overriding:
methods overriding: "rectangle" and "triangle" override getArea() method (declared in the superclass abstract "figure")
to override a method you MUST declare it with the same signature (name + number + arguments sequence)

superclass method calling:
figure declare a method to get area and a contructor, overridden in the class "square"

//abstract
abstract class figure
{
private $priv;
protected
$w, $h;
protected
$prot;
public
$pub;

public function
__construct($w, $h) {
$this->w = $w; $this->h = $h;
}
abstract public function getArea();
}

class
triangle extends figure
{
public function getArea() { return $this->w*$this->h/2; }
}

class
rectangle extends figure
{
public function getArea() { return $this->w*$this->h; }
}

class
square extends rectangle
{
//constructor . overriding ??
public function __construct($w){
//call superclass ctor
parent::__construct($w, $w);
}
}

$r = new rectangle(10,20);
print
$r->getArea(); //200

$t = new triangle(10,20);
print
$t->getArea(); //100

$s = new square(11);
print
$s->getArea(); //121

 

PHP and tips|PHP