Friday, September 14, 2012

Members, __set, __get, ArrayAccess and Iterator

Lessons learned:
  • __set() is 5 times slower than setting a member
  • __get() + __set() is 13 times slower than incrementing a member
  • Iterator is 4 times slower than using a member
  • ArrayAccess is 3 times slower than setting an element in a member array
  • ArrayAccess is 6 times slower than incrementing an element in a member array

Here is the code:
class test1 {
  public $test = null;
  private $_test = null;

  public function __set($id, $val) {
    $this->_test = $val;
  }
}

$start = microtime(true);
$c = new test1();
for ($i=0; $i<1000000; $i++) $c->test = $i;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.1830s

$start = microtime(true);
$c = new test1();
for ($i=0; $i<1000000; $i++) $c->test2 = $i;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.9570s


class test2 {
  private $_data = ['test4'=>0];
  public $test3 = 0;

  public function __set($id, $val) {
    $this->_data[$id] = $val;
  }
  public function __get($id) {
    return $this->_data[$id];
  }
}

$start = microtime(true);
$c = new test2();
for ($i=0; $i<1000000; $i++) $c->test3++;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.1495s

$start = microtime(true);
$c = new test2();
for ($i=0; $i<1000000; $i++) $c->test4++;
echo number_format(microtime(true)-$start, 4)."\n"; // 2.0083s


class test3 implements ArrayAccess {
  private $_data = [0];
  public $data = [0];
  
  public function offsetSet($key, $val) {
    $this->_data[$key] = $val;
  }
  public function offsetGet($key) {
    return $this->_data[$key];
  }
  public function offsetExists($key) {
    return isset($this->_data[$key]);
  }
  public function offsetUnset($key) {
    unset($this->_data[$key]);
  }
}

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c->data[0] = $i;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.2739s

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c[0] = $i;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.9724s

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c->data[0]++;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.2694s

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c[0] = $c[0]+1; // $c[0]++ does not work here
echo number_format(microtime(true)-$start, 4)."\n"; // 1.6771s

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c->data[] = $i;
echo number_format(microtime(true)-$start, 4)."\n"; // 0.4906s

$start = microtime(true);
$c = new test3();
for ($i=0; $i<1000000; $i++) $c[$i] = $i; // $c[] does not work here
echo number_format(microtime(true)-$start, 4)."\n"; // 1.3456s


class test4 {
  public $data = [];
  
  public function __construct() {
    $this->data = range(0,500000);
  }
}

$start = microtime(true);
$c = new test4();
foreach ($c->data as $val) {}
echo number_format(microtime(true)-$start, 4)."\n"; // 0.2541s

$start = microtime(true);
$c = new test4();
foreach ($c->data as $key=>$val) {}
echo number_format(microtime(true)-$start, 4)."\n"; // 0.2704s


class test5 implements Iterator {
  private $_pos = 0;
  private $_data = [];

  public function __construct() {
    $this->_data = range(0,500000);
  }
  function rewind() {
    $this->_pos = 0;
  }
  function current() {
    return $this->_data[$this->_pos];
  }
  function key() {
    return $this->_pos;
  }
  function next() {
    $this->_pos++;
  }
  function valid() {
    return isset($this->_data[$this->_pos]);
  }
}

$start = microtime(true);
$c = new test5();
foreach ($c as $val) {}
echo number_format(microtime(true)-$start, 4)."\n"; // 0.9770s

$start = microtime(true);
$c = new test5();
foreach ($c as $key=>$val) {}
echo number_format(microtime(true)-$start, 4)."\n"; // 1.0400s
Tested with PHP 5.4.5

No comments:

Post a Comment

Labels

performance (23) benchmark (6) MySQL (5) architecture (5) coding style (5) memory usage (5) HHVM (4) C++ (3) Java (3) Javascript (3) MVC (3) SQL (3) abstraction layer (3) framework (3) maintenance (3) Go (2) Golang (2) HTML5 (2) ORM (2) PDF (2) Slim (2) Symfony (2) Zend Framework (2) Zephir (2) firewall (2) log files (2) loops (2) quality (2) real-time (2) scrum (2) streaming (2) AOP (1) Apache (1) Arrays (1) C (1) DDoS (1) Deployment (1) DoS (1) Dropbox (1) HTML to PDF (1) HipHop (1) OCR (1) OOP (1) Objects (1) PDO (1) PHP extension (1) PhantomJS (1) SPL (1) SQLite (1) Server-Sent Events (1) Silex (1) Smarty (1) SplFixedArray (1) Unicode (1) V8 (1) analytics (1) annotations (1) apc (1) archiving (1) autoloading (1) awk (1) caching (1) code quality (1) column store (1) common mistakes (1) configuration (1) controller (1) decisions (1) design patterns (1) disk space (1) dynamic routing (1) file cache (1) garbage collector (1) good developer (1) html2pdf (1) internationalization (1) invoice (1) just-in-time compiler (1) kiss (1) knockd (1) legacy code (1) legacy systems (1) logtop (1) memcache (1) memcached (1) micro framework (1) ncat (1) node.js (1) openssh (1) pfff (1) php7 (1) phpng (1) procedure models (1) ramdisk (1) recursion (1) refactoring (1) references (1) regular expressions (1) search (1) security (1) sgrep (1) shm (1) sorting (1) spatch (1) ssh (1) strange behavior (1) swig (1) template engine (1) threads (1) translation (1) ubuntu (1) ufw (1) web server (1) whois (1)