Overload the behavior of count() when called on certain objects [duplicate]
It sounds like you want to implement the Countable
interface:
class a implements Countable { public function __construct() { $this->list = array("1", "2"); } public function count() { return count($this->list); }}$blah = new a();echo count($blah); // 2
tl;dr - answer is at the bottom :)
In PHP, this model is reversed; rather than overloading functions (not methods) with different argument types, each class is meant to define magic methods for each of those functions.
Below is the list of functions that magic behaviour can be defined for inside your class. In the examples, each reference to $obj
is an instance of your class, ->unknown
refers to a missing property and ->blamethod()
refers to a missing method.
__toString()
- this method is called when your object is used in a string context, e.g.echo "My object is: $obj\n";
__invoke([$arg1..n])
- when your object is used as a function, this method gets called, e.g.$obj($a, $b);
__get($prop)
- allows for intercepting an attempt to access a non-existing property of your class, e.g.$obj->unknown
; btw, this can sometimes be used as a way to lazy load certain properties that would otherwise take a considerable amount of processing when done in the constructor.__set($prop, $value)
- gets called when a non-existing property is being set, e.g.$obj->unknown = 42;
__isset($prop)
- called to determine the existence of a non-existing property (I realize how funny that sounds), e.g.isset($obj->unknown)
would call$obj->__isset('unknown')
__unset($prop)
- called in cases like theseunset($obj->unknown);
__call($name, $arguments)
- intercepts a call to an unimplemented method of your class, e.g.$obj->blamethod(1, 2, 3);
will invoke$obj->__call('blamethod', array(1, 2, 3));
__callStatic($name, $arguments)
- like__call()
but you will not be able to use$this
inside your implementation.__clone() - called when
$x = clone $obj;
is called, so you get to decide what data is kept and what's thrown away.
With SPL, a few more concepts were introduced by means of implementing certain interfaces:
Traversable
- an abstract interface that defines what your class does when used in aforeach
construct; the concrete interface is calledIterator
.ArrayAccess
- an interface that allows using instances of your class to be used like an array.Serializable
- an interface that defines two methods to be called uponserialize()
orunserialize()
. It's mutually exclusive to using__sleep()
and__wakeup()
.Countable
- defines one method to be called whenevercount()
is performed on your class instance.