Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /**
- * test shallowCopy vs deepCopy
- *
- * shallowCopy:
- * \code
- * <Test>
- * - array with closure
- * - property with object <closure>
- * - property with object <Alice>
- * - array with object <closure>
- * - property with object <closure>
- * - property with object <Bob>
- * - private var
- * - public var
- * - static object <DefaultObject>
- * - protected var
- * \endcode
- *
- * Actions of shallowCopy:
- * - create new Test2
- * - copy values from <Test>
- * - don't touch statics
- * - property with object (not closure): copy reference, not the object
- * - property with object closure: rebind closure to <Test2>
- * - property array with objects of type closure: recursively search closures and rebind them to <Test2>
- *
- * deepCopy:
- * \code
- * <Test>
- * - array with closure
- * - property with object <closure>
- * - property with object <Alice>
- * - array with object <closure>
- * - property with object <closure>
- * - property with object <Bob>
- * - private var
- * - public var
- * - static object <DefaultObject>
- * - protected var
- * \endcode
- *
- * Actions of deepCopy:
- * - create new Test2
- * - copy values from <Test>
- * - don't touch statics
- * - property with object (not closure): object<IDefaultObject>->deepCopy, clone other objects
- * - property with object closure: rebind closure to <Test2>
- * - property array with objects (not closure): object<IDefaultObject>->deepCopy, clone other objects
- * - property array with objects of type closure: recursively search closures and rebind them to <Test2>
- *
- * \todo How to handle closures in traversable objects?
- */
- class test extends DefaultObject
- {
- private $name = 'base.name.notSet'; // name in multiple subjects are identical when closures are in old context
- public $aV = 'base.av.notSet'; // av: arrayValue
- public $sV = 'base.sv.notSet'; // sv: selfValue
- private $private = 0;
- static $static = 0;
- protected $alice = NULL; // object as property
- protected $fnA = []; // closure in array
- protected $fnC = NULL; // closure as property
- function __construct($name, Alice $alice, $private, DefaultObject $static)
- {
- $this->name = $name;
- $this->alice = $alice;
- $this->private = $private;
- self::$static = $static;
- $this->fnA['test']['self'] = function(){ return $this->aV; };
- $this->fnC = function(){ return $this->sV; };
- $this->set('init'.$name);
- }
- function __debugInfo()
- {
- return
- [
- 'name' => $this->name,
- //'aV' => $this->aV,
- //'sV' => $this->sV,
- 'private' => $this->private,
- 'alice' => $this->alice,
- 'static' => self::$static,
- 'arrayClosure' => $this->fnA['test']['self'],
- 'propClosure' => $this->fnC,
- ];
- }
- function setClassName($n)
- {
- $this->name = $n;
- }
- function setAV($self, $alice)
- {
- $this->aV = 'base.av.'.$self;
- $this->alice->aV = 'alic.av.'.$alice;
- }
- function setSV($self, $alice)
- {
- $this->sV = 'base.sv.'.$self;
- $this->alice->sV = 'alic.sv.'.$alice;
- }
- function set($n)
- {
- $this->setAV('arrayClosure.'.$this->name.'.'.$n, 'arrayClosure.'.$this->name.'.'.$n);
- $this->setSV('propertyClosure.'.$this->name.'.'.$n, 'propertyClosure.'.$this->name.'.'.$n);
- }
- function closureInArray()
- {
- $fn = $this->fnA['test']['self'];
- echo 'closure in array: '.$fn().PHP_EOL
- .' '.$this->alice->aT();
- }
- function closureAsProperty()
- {
- $fn = $this->fnC;
- echo 'closure as property:'.$fn().PHP_EOL
- .' '.$this->alice->sT();
- }
- function testClosureScope()
- {
- $this->closureInArray();
- $this->closureAsProperty();
- }
- function compare(test $__Test)
- {
- $r = [];
- $r['Test'] = $this === $__Test;
- $r['Test->fnA'] = $this->fnA === $__Test->fnA;
- $r['Test->fnC'] = $this->fnC === $__Test->fnC;
- $r['Test->alice'] = $this->alice->compare($__Test->alice);
- $r['Test::static'] = self::$static === $__Test::$static;
- return ["Compare {$this->name} with {$__Test->name}" => $r];
- }
- }
- class bob
- {
- }
- class alice extends DefaultObject
- {
- public $aV = 'alice.av.notSet';
- public $sV = 'alice.sv.notSet';
- protected $fnA = [];
- protected $fnC = NULL;
- protected $__bob;
- function __construct()
- {
- $this->fnA['test']['alice'] = function(){ return $this->aV;};
- $this->fnC = function(){ return $this->sV; };
- $this->__bob = new bob;
- }
- function __debugInfo()
- {
- return
- [
- //'aV' => $this->aV,
- //'sV' => $this->sV,
- 'arrayClosure' => $this->fnA['test']['alice'],
- //'propClosure' => $this->fnC,
- ];
- }
- function aT()
- {
- $fn = $this->fnA['test']['alice'];
- return $fn().PHP_EOL;
- }
- function sT()
- {
- $fn = $this->fnC;
- return $fn().PHP_EOL;
- }
- function compare(alice $__Test)
- {
- $r = [];
- $r['alice'] = $this === $__Test;
- $r['alice->fnA'] = $this->fnA === $__Test->fnA;
- $r['alice->fnC'] = $this->fnC === $__Test->fnC;
- $r['alice->__bob'] = $this->__bob === $__Test->__bob;
- return $r;
- }
- }
- $refTest = 'foooooooooooobar';
- echo '#--start closure test', PHP_EOL;
- $T = new Test('ORIG', new alice, $refTest, new DefaultObject);
- $T->set('$T.ready');
- $T->closureAsProperty(); // base name 'orig', alice name 'orig'
- echo '#----should be the same as above', PHP_EOL;
- $T->closureInArray(); // base name 'orig', alice name 'orig'
- echo '#--create shallow copy $D', PHP_EOL;
- $D = $T->shallowCopy();
- $T->set('$T.afterShallowCopy');
- $D->set('$D.afterShallowCopy');
- $T->closureAsProperty(); // base name 'orig', alice name 'orig'
- $D->closureAsProperty(); // base name 'orig', alice name 'orig'
- echo '#----should be the same as above', PHP_EOL;
- $T->closureInArray(); // base name 'orig', alice name 'orig'
- $D->closureInArray(); // base name 'orig', alice name 'orig'
- echo '#--change name of $D to "COPY"', PHP_EOL;
- $D->setClassName('COPY');
- $T->set('$T.afterNameChange$D');
- $D->set('$D.afterNameChange$D');
- echo '#----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object', PHP_EOL;
- $T->closureAsProperty(); // base name 'orig', alice name 'copy'
- $D->closureAsProperty(); // base name 'copy', alice name 'copy'
- echo '#----should be the same as above', PHP_EOL;
- $T->closureInArray(); // base name 'orig', alice name 'copy'
- $D->closureInArray(); // base name 'copy', alice name 'copy'
- echo '#--create deep $E', PHP_EOL;
- $E = $T->deepCopy();
- $T->set('$T.afterDeepCopy');
- $D->set('$D.afterDeepCopy');
- $E->set('$E.afterDeepCopy');
- echo '#----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object', PHP_EOL;
- $T->closureAsProperty(); // base name 'orig', alice name 'orig'
- $D->closureAsProperty(); // base name 'orig', alice name 'orig'
- $E->closureAsProperty(); // base name 'orig', alice name 'orig'
- $T->closureInArray(); // base name 'orig', alice name 'orig'
- $D->closureInArray(); // base name 'orig', alice name 'orig'
- $E->closureInArray(); // base name 'orig', alice name 'orig'
- echo '#--change name of $E to "DEEP"', PHP_EOL;
- $E->setClassName('DEEP');
- $T->set('$T.afterNameChange$E');
- $D->set('$D.afterNameChange$E');
- $E->set('$E.afterNameChange$E');
- echo '#----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object', PHP_EOL;
- $T->closureAsProperty(); // base name 'orig', alice name 'orig'
- $D->closureAsProperty(); // base name 'orig', alice name 'orig'
- echo '#----both should be DEEP', PHP_EOL;
- $E->closureAsProperty(); // base name 'orig', alice name 'orig'
- echo '#----should be the same as above', PHP_EOL;
- $T->closureInArray(); // base name 'orig', alice name 'orig'
- $D->closureInArray(); // base name 'orig', alice name 'orig'
- $E->closureInArray(); // base name 'orig', alice name 'orig'
- var_dump($T->compare($D));
- var_dump($T->compare($E));
- echo '#--dump of "ORIG" ############################################################################', PHP_EOL;
- var_dump($T);
- echo '#--dump of "COPY" ############################################################################', PHP_EOL;
- var_dump($D);
- echo '#--dump of "DEEP" ############################################################################', PHP_EOL;
- var_dump($E);
- // output:
- /*
- #--start closure test
- closure as property:base.sv.propertyClosure.ORIG.$T.ready
- alic.sv.propertyClosure.ORIG.$T.ready
- #----should be the same as above
- closure in array: base.av.arrayClosure.ORIG.$T.ready
- alic.av.arrayClosure.ORIG.$T.ready
- #--create shallow copy $D
- closure as property:base.sv.propertyClosure.ORIG.$T.afterShallowCopy
- alic.sv.propertyClosure.ORIG.$D.afterShallowCopy
- closure as property:base.sv.propertyClosure.ORIG.$D.afterShallowCopy
- alic.sv.propertyClosure.ORIG.$D.afterShallowCopy
- #----should be the same as above
- closure in array: base.av.arrayClosure.ORIG.$T.afterShallowCopy
- alic.av.arrayClosure.ORIG.$D.afterShallowCopy
- closure in array: base.av.arrayClosure.ORIG.$D.afterShallowCopy
- alic.av.arrayClosure.ORIG.$D.afterShallowCopy
- #--change name of $D to "COPY"
- #----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object
- closure as property:base.sv.propertyClosure.ORIG.$T.afterNameChange$D
- alic.sv.propertyClosure.COPY.$D.afterNameChange$D
- closure as property:base.sv.propertyClosure.COPY.$D.afterNameChange$D
- alic.sv.propertyClosure.COPY.$D.afterNameChange$D
- #----should be the same as above
- closure in array: base.av.arrayClosure.ORIG.$T.afterNameChange$D
- alic.av.arrayClosure.COPY.$D.afterNameChange$D
- closure in array: base.av.arrayClosure.COPY.$D.afterNameChange$D
- alic.av.arrayClosure.COPY.$D.afterNameChange$D
- #--create deep $E
- #----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object
- closure as property:base.sv.propertyClosure.ORIG.$T.afterDeepCopy
- alic.sv.propertyClosure.COPY.$D.afterDeepCopy
- closure as property:base.sv.propertyClosure.COPY.$D.afterDeepCopy
- alic.sv.propertyClosure.COPY.$D.afterDeepCopy
- closure as property:base.sv.propertyClosure.ORIG.$E.afterDeepCopy
- alic.sv.propertyClosure.ORIG.$E.afterDeepCopy
- closure in array: base.av.arrayClosure.ORIG.$T.afterDeepCopy
- alic.av.arrayClosure.COPY.$D.afterDeepCopy
- closure in array: base.av.arrayClosure.COPY.$D.afterDeepCopy
- alic.av.arrayClosure.COPY.$D.afterDeepCopy
- closure in array: base.av.arrayClosure.ORIG.$E.afterDeepCopy
- alic.av.arrayClosure.ORIG.$E.afterDeepCopy
- #--change name of $E to "DEEP"
- #----closure in ALICE returns COPY: because ORIG and COPY referencing to the same ALICE object
- closure as property:base.sv.propertyClosure.ORIG.$T.afterNameChange$E
- alic.sv.propertyClosure.COPY.$D.afterNameChange$E
- closure as property:base.sv.propertyClosure.COPY.$D.afterNameChange$E
- alic.sv.propertyClosure.COPY.$D.afterNameChange$E
- #----both should be DEEP
- closure as property:base.sv.propertyClosure.DEEP.$E.afterNameChange$E
- alic.sv.propertyClosure.DEEP.$E.afterNameChange$E
- #----should be the same as above
- closure in array: base.av.arrayClosure.ORIG.$T.afterNameChange$E
- alic.av.arrayClosure.COPY.$D.afterNameChange$E
- closure in array: base.av.arrayClosure.COPY.$D.afterNameChange$E
- alic.av.arrayClosure.COPY.$D.afterNameChange$E
- closure in array: base.av.arrayClosure.DEEP.$E.afterNameChange$E
- alic.av.arrayClosure.DEEP.$E.afterNameChange$E
- array(1) {
- ["Compare ORIG with COPY"]=>
- array(5) {
- ["Test"]=>
- bool(false)
- ["Test->fnA"]=>
- bool(false)
- ["Test->fnC"]=>
- bool(false)
- ["Test->alice"]=>
- array(4) {
- ["alice"]=>
- bool(true)
- ["alice->fnA"]=>
- bool(true)
- ["alice->fnC"]=>
- bool(true)
- ["alice->__bob"]=>
- bool(true)
- }
- ["Test::static"]=>
- bool(true)
- }
- }
- array(1) {
- ["Compare ORIG with DEEP"]=>
- array(5) {
- ["Test"]=>
- bool(false)
- ["Test->fnA"]=>
- bool(false)
- ["Test->fnC"]=>
- bool(false)
- ["Test->alice"]=>
- array(4) {
- ["alice"]=>
- bool(false)
- ["alice->fnA"]=>
- bool(false)
- ["alice->fnC"]=>
- bool(false)
- ["alice->__bob"]=>
- bool(false)
- }
- ["Test::static"]=>
- bool(true)
- }
- }
- #--dump of "ORIG" ############################################################################
- object(web\test)#2 (6) {
- ["name"]=>
- string(4) "ORIG"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#8 (1) {
- ["this"]=>
- object(web\test)#2 (6) {
- ["name"]=>
- string(4) "ORIG"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- object(Closure)#9 (1) {
- ["this"]=>
- object(web\test)#2 (6) {
- ["name"]=>
- string(4) "ORIG"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
- }
- ["propClosure"]=>
- object(Closure)#9 (1) {
- ["this"]=>
- object(web\test)#2 (6) {
- ["name"]=>
- string(4) "ORIG"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#8 (1) {
- ["this"]=>
- object(web\test)#2 (6) {
- ["name"]=>
- string(4) "ORIG"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
- #--dump of "COPY" ############################################################################
- object(web\test)#12 (6) {
- ["name"]=>
- string(4) "COPY"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#29 (1) {
- ["this"]=>
- object(web\test)#12 (6) {
- ["name"]=>
- string(4) "COPY"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- object(Closure)#30 (1) {
- ["this"]=>
- object(web\test)#12 (6) {
- ["name"]=>
- string(4) "COPY"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
- }
- ["propClosure"]=>
- object(Closure)#30 (1) {
- ["this"]=>
- object(web\test)#12 (6) {
- ["name"]=>
- string(4) "COPY"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#29 (1) {
- ["this"]=>
- object(web\test)#12 (6) {
- ["name"]=>
- string(4) "COPY"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- object(Closure)#4 (1) {
- ["this"]=>
- object(web\alice)#3 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
- #--dump of "DEEP" ############################################################################
- object(web\test)#26 (6) {
- ["name"]=>
- string(4) "DEEP"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- object(Closure)#45 (1) {
- ["this"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#44 (1) {
- ["this"]=>
- object(web\test)#26 (6) {
- ["name"]=>
- string(4) "DEEP"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- object(Closure)#45 (1) {
- ["this"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- object(Closure)#43 (1) {
- ["this"]=>
- object(web\test)#26 (6) {
- ["name"]=>
- string(4) "DEEP"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- object(Closure)#45 (1) {
- ["this"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
- }
- ["propClosure"]=>
- object(Closure)#43 (1) {
- ["this"]=>
- object(web\test)#26 (6) {
- ["name"]=>
- string(4) "DEEP"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- object(Closure)#45 (1) {
- ["this"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- object(Closure)#44 (1) {
- ["this"]=>
- object(web\test)#26 (6) {
- ["name"]=>
- string(4) "DEEP"
- ["private"]=>
- string(16) "foooooooooooobar"
- ["alice"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- object(Closure)#45 (1) {
- ["this"]=>
- object(web\alice)#34 (1) {
- ["arrayClosure"]=>
- *RECURSION*
- }
- }
- }
- ["static"]=>
- object(ILLI\Core\Std\DefaultObject)#7 (0) {
- }
- ["arrayClosure"]=>
- *RECURSION*
- ["propClosure"]=>
- *RECURSION*
- }
- }
- ["propClosure"]=>
- *RECURSION*
- }
- }
- }
Add Comment
Please, Sign In to add comment