Northie
08-18-2008, 03:12 PM
I'm in the middle of building myself a PHP 5 framework and i am utilising such features as __autolaod() and the singleton design pattern.
I use singletons to persist data around a request that may invoke over 20 different objects......then i read about 'overloading' - a way to dynamically create class members and methods - and came up with this:
class myVars {
/**
* @var object instance of self, see public static function myVars()
*/
private static $instance;
/**
* @var settings held here
*/
public $data = array();
/**
* private construct, does nothing
*/
private function __contrsuct() {
}
/**
* @return object an instance of it's self
*/
public static function Load() {
if (!isset(self::$instance)) {
$c = __CLASS__;
self::$instance = new $c;
}
return self::$instance;
}
/**
* __set
* magic method called when overloading the object
*
* @param str $key name of variable, used as array key
* @param mixed $value Value of variable
* @return bool an instance of it's self
*/
public function __set($key,$value) {
$this->data[$key] = $value;
return true;
}
/**
* __get
* magic method called when retrieving overloaded object member
*
* @param str $key name of variable, used as array key
* @return mixed value of key or null
*/
public function __get($key) {
if(array_key_exists($key,$this->data)) {
return $this->data[$key];
} else {
return null;
}
}
/**
* Prevent cloning
*/
public function __clone() {
trigger_error('Clone is not allowed.', E_USER_ERROR);
}
}
Example 1
Explicit call to class name
Gloabal in all contexts where the class is defined
myVars::Load()->a = 'Hello World';
echo myVars::Load()->a; //echos Hello World
Example 2
Instance of object created
Retains the scope of $o
$o = myVars::Load();
$o->b = 'Hello Again';
echo $o->b; //echos Hello Again
Example 3
use inside another object
retains scope of instance, but two different class members (even with different visibility) can access the 'global' variables
class someExample {
public $myGlobals = "";
private $myPrivGlobals = "";
public function __construct() {
$this->myGlobals = myVars::Load();
$this->myPrivGlobals = myVars::Load();
$this->egFn();
}
private function egFn() {
$this->myPrivGlobals->c = 'Still here?'."<br />\n";
}
public function egFn2() {
echo $this->myGlobals->a; //Hello World
echo $this->myGlobals->b; //Hello Again
echo $this->myGlobals->c; //Still here?
echo $this->myPrivGlobals->c; //Still here?
}
}
$x = new someExample;
$x->egFn2();
I thought this was quite interesting (call me a geek!) and would be interested in other people's thoughts
possible further reading:
http://www.php.net/manual/en/language.oop5.patterns.php
http://www.php.net/manual/en/language.oop5.overloading.php
http://www.php.net/manual/en/language.oop5.autoload.php
I parse an ini file of settings and class names/locations into a singleton, and then access tis singleton in the __autoload function
I use singletons to persist data around a request that may invoke over 20 different objects......then i read about 'overloading' - a way to dynamically create class members and methods - and came up with this:
class myVars {
/**
* @var object instance of self, see public static function myVars()
*/
private static $instance;
/**
* @var settings held here
*/
public $data = array();
/**
* private construct, does nothing
*/
private function __contrsuct() {
}
/**
* @return object an instance of it's self
*/
public static function Load() {
if (!isset(self::$instance)) {
$c = __CLASS__;
self::$instance = new $c;
}
return self::$instance;
}
/**
* __set
* magic method called when overloading the object
*
* @param str $key name of variable, used as array key
* @param mixed $value Value of variable
* @return bool an instance of it's self
*/
public function __set($key,$value) {
$this->data[$key] = $value;
return true;
}
/**
* __get
* magic method called when retrieving overloaded object member
*
* @param str $key name of variable, used as array key
* @return mixed value of key or null
*/
public function __get($key) {
if(array_key_exists($key,$this->data)) {
return $this->data[$key];
} else {
return null;
}
}
/**
* Prevent cloning
*/
public function __clone() {
trigger_error('Clone is not allowed.', E_USER_ERROR);
}
}
Example 1
Explicit call to class name
Gloabal in all contexts where the class is defined
myVars::Load()->a = 'Hello World';
echo myVars::Load()->a; //echos Hello World
Example 2
Instance of object created
Retains the scope of $o
$o = myVars::Load();
$o->b = 'Hello Again';
echo $o->b; //echos Hello Again
Example 3
use inside another object
retains scope of instance, but two different class members (even with different visibility) can access the 'global' variables
class someExample {
public $myGlobals = "";
private $myPrivGlobals = "";
public function __construct() {
$this->myGlobals = myVars::Load();
$this->myPrivGlobals = myVars::Load();
$this->egFn();
}
private function egFn() {
$this->myPrivGlobals->c = 'Still here?'."<br />\n";
}
public function egFn2() {
echo $this->myGlobals->a; //Hello World
echo $this->myGlobals->b; //Hello Again
echo $this->myGlobals->c; //Still here?
echo $this->myPrivGlobals->c; //Still here?
}
}
$x = new someExample;
$x->egFn2();
I thought this was quite interesting (call me a geek!) and would be interested in other people's thoughts
possible further reading:
http://www.php.net/manual/en/language.oop5.patterns.php
http://www.php.net/manual/en/language.oop5.overloading.php
http://www.php.net/manual/en/language.oop5.autoload.php
I parse an ini file of settings and class names/locations into a singleton, and then access tis singleton in the __autoload function