Advertisement
fruffl

AbstractDataType Builder

Feb 19th, 2013
125
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
PHP 7.32 KB | None | 0 0
  1. <?PHP
  2.     NAMESPACE ILLI\Core\Std\Def;
  3.     USE ILLI\Core\Std\Def\__const_Type;
  4.     USE ILLI\Core\Std\Def\ADT\ComponentInitializationException;
  5.     USE ILLI\Core\Std\Def\ADT\ComponentMethodCallException;
  6.     USE ILLI\Core\Std\Exception\ArgumentExpectedException;
  7.     USE ILLI\Core\Std\Exception\ArgumentLengthZeroException;
  8.     USE ILLI\Core\Std\Exception\ArgumentInUseException;
  9.     USE ILLI\Core\Std\Exception\NotSupportedException;
  10.     USE ILLI\Core\Std\Spl\Fsb;
  11.     USE ILLI\Core\Util\Spl;
  12.    
  13.     CLASS ADT EXTENDS \ILLI\Core\Std\Spl\Fsb
  14.     {
  15.         /**
  16.          * cache typedef request
  17.          *
  18.          * :hashAddr<string>
  19.          *  instance of get_called_class(): ILLI\Core\Std\Def\ADT*
  20.          *  instance of __CLASS__:      ILLI\Core\Std\Def\ADT<hash>
  21.          *
  22.          * :adtDef<ILLI\Core\Std\Spl\Fsb>
  23.          *  collection of defined __const_Type(s)
  24.          *
  25.          * @var     array [{:hashAddr} => {:adtDef}]
  26.          */
  27.         private static $__gc = [];
  28.        
  29.         /**
  30.          * Instantiate a new Abstract Data Type.
  31.          *
  32.          * define ADT
  33.          *
  34.          * :offset<long>
  35.          *  zero-based index
  36.          *
  37.          * :gcType<string>
  38.          *  a valid __const_Type
  39.          *
  40.          * @param   array $__defineTypes [{:offset} => {:gcType}]
  41.          * @throws  ILLI\Core\Std\Exception\ADT\ComponentInitializationException
  42.          * @see     ILLI\Core\Std\Def\__const_Type
  43.          * @see     ILLI\Core\Std\Def\ADTInstance
  44.          * @see     ILLI\Core\Std\Spl\Fsb
  45.          */
  46.         public function __construct(array $__defineTypes = [])
  47.         {
  48.             try
  49.             {
  50.                 if([] === $__defineTypes)
  51.                     throw new ArgumentLengthZeroException;
  52.                
  53.                 $n = $this->createHashAddr($__defineTypes);
  54.                 $t = &self::$__gc[$n];     
  55.                
  56.                 parent::setSize(1);
  57.                 parent::offsetSet(0, $n);
  58.                
  59.                 if(FALSE === isset($t))
  60.                     $t = Fsb::fromArray($this->parseDef($__defineTypes));
  61.             }
  62.             catch(\Exception $E)
  63.             {
  64.                 throw new ComponentInitializationException($E, ['class' => get_called_class()]);
  65.             }
  66.         }
  67.        
  68.         /**
  69.          * value validation
  70.          *
  71.          * The type of given value equals with one of the registered gc-types
  72.          *
  73.          * @param   mixed $__value
  74.          * @return  boolean
  75.          * @see     ILLI\Core\Std\Def\__const_Type
  76.          */
  77.         public function validate($__value)
  78.         {
  79.             try
  80.             {
  81.                 $v = &$__value;
  82.                 $t = getType($v);
  83.                
  84.                 foreach($this->getGC() as $h)
  85.                 {
  86.                     if($t === $h
  87.                     ||($t === __const_Type::SPL_OBJECT && (class_exists($h) || interface_exists($h)) && (is_subclass_of($v, $h) || $v instanceOf $h)))
  88.                         return TRUE;
  89.                 }
  90.                
  91.                 return FALSE;
  92.             }
  93.             catch(\Exception $E)
  94.             {
  95.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_VALIDATE, ['method' => __METHOD__]);
  96.             }
  97.         }
  98.        
  99.         /**
  100.          * get ADT-gc hash address
  101.          *
  102.          * @return  string
  103.          * @see     ::$__gc
  104.          */
  105.         public function getName()
  106.         {
  107.             try
  108.             {
  109.                 return parent::offsetGet(0);
  110.             }
  111.             catch(\Exception $E)
  112.             {
  113.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_GET_NAME, ['method' => __METHOD__]);
  114.             }
  115.         }
  116.        
  117.         /**
  118.          * get ADT-gc
  119.          *
  120.          * @return  ILLI\Core\Std\Spl\Fsb
  121.          * @see     ::$__gc
  122.          */
  123.         public function getGC()
  124.         {
  125.             try
  126.             {
  127.                 return self::$__gc[$this->getName()];
  128.             }
  129.             catch(\Exception $E)
  130.             {
  131.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_GET_GC, ['method' => __METHOD__]);
  132.             }
  133.         }
  134.        
  135.         /**
  136.          * join registered gc-type(s)
  137.          *
  138.          * @return  ILLI\Core\Std\Spl\Fsb
  139.          * @see     ::$__gc
  140.          * @see     ILLI\Core\Std\Def\__const_Type
  141.          */
  142.         public function toString()
  143.         {
  144.             try
  145.             {
  146.                 return implode('|', $this->getGC()->toArray());
  147.             }
  148.             catch(\Exception $E)
  149.             {
  150.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_TO_STRING, ['method' => __METHOD__]);
  151.             }
  152.         }
  153.        
  154.         /**
  155.          * generate gc-hash-address from called-class or from spl_object_hash
  156.          *
  157.          * :offset<long>
  158.          *  zero-based index
  159.          *
  160.          * :gcType<string>
  161.          *  a valid __const_Type
  162.          *
  163.          * @param   array $__defineTypes [{:offset} => {:gcType}]
  164.          * @return  string
  165.          * @see     ::$__gc
  166.          */
  167.         protected function createHashAddr(array $__defineTypes = [])
  168.         {
  169.             try
  170.             {
  171.                 #~ performanced ADT: cache request by called-class; otherwise by hash
  172.                 return ($c = get_called_class()) === __CLASS__ ? Spl::nameWithHash($c, $this) : $c;
  173.             }
  174.             catch(\Exception $E)
  175.             {
  176.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_CREATE_HASH_ADDR, ['method' => __METHOD__]);
  177.             }
  178.         }
  179.        
  180.         /**
  181.          * validate typedef request
  182.          *
  183.          * :offset<long>
  184.          *  zero-based index
  185.          *
  186.          * :gcType<string>
  187.          *  a valid __const_Type
  188.          *
  189.          * @param   array $__defineTypes [{:offset} => {:gcType}]
  190.          * @throws  ILLI\Core\Std\Exception\ArgumentExpectedException when {:gcType} is not a string
  191.          */
  192.         protected function parseDef(array $__defineTypes)
  193.         {
  194.             try
  195.             {
  196.                 $r = [];
  197.                
  198.                 foreach($__defineTypes as $k => $v)
  199.                 {
  200.                     if(FALSE === is_string($v))
  201.                         throw new ArgumentExpectedException([
  202.                             'target'    => $this->getName().'['.$k.']',
  203.                             'expected'  => 'string',
  204.                             'detected'  => $t = getType($v),
  205.                             'value'     => is_object($v)
  206.                                         ? get_class($v)
  207.                                         : ((is_string($v) && (class_exists($v) || interface_exists($v))) || is_scalar($v)) ? $v : $t
  208.                         ]);
  209.                        
  210.                     $r[$k] = $v;
  211.                 }
  212.                
  213.                 if([] === $r)
  214.                     throw new ArgumentLengthZeroException;
  215.                
  216.                 return $r;
  217.             }
  218.             catch(\Exception $E)
  219.             {
  220.                 throw new ComponentMethodCallException($E, ComponentMethodCallException::ERROR_PARSE_DEF, ['method' => __METHOD__]);
  221.             }
  222.         }
  223.        
  224.         #:ILLI\Core\Std\Spl\Fsb:
  225.             #:NotSupported:
  226.             /**
  227.              * @notSupported
  228.              * @throws  ILLI\Core\Std\Exception\NotSupportedException
  229.              */
  230.             public function setSize($__size)
  231.             {
  232.                 throw new NotSupportedException([
  233.                     'target' => __METHOD__
  234.                 ]);
  235.             }
  236.            
  237.             /**
  238.              * @notSupported
  239.              * @throws  ILLI\Core\Std\Exception\NotSupportedException
  240.              */
  241.             public function offsetSet($__offset, $__value)
  242.             {
  243.                 throw new NotSupportedException([
  244.                     'target' => __METHOD__
  245.                 ]);
  246.             }
  247.            
  248.             /**
  249.              * @notSupported
  250.              * @throws  ILLI\Core\Std\Exception\NotSupportedException
  251.              */
  252.             public function offsetUnset($__offset)
  253.             {
  254.                 throw new NotSupportedException([
  255.                     'target' => __METHOD__
  256.                 ]);
  257.             }
  258.             #::
  259.            
  260.             #:gc:
  261.             public function getSize()
  262.             {
  263.                 return $this->getGC()->getSize();
  264.             }
  265.            
  266.             public function offsetGet($__offset)
  267.             {
  268.                 return $this->getGC()->offsetGet($__offset);
  269.             }
  270.            
  271.             public function offsetExists($__offset)
  272.             {
  273.                 return $this->getGC()->offsetExists($__offset);
  274.             }
  275.            
  276.             public function rewind()
  277.             {
  278.                 return $this->getGC()->rewind();
  279.             }
  280.            
  281.             public function end()
  282.             {
  283.                 return $this->getGC()->end();
  284.             }
  285.            
  286.             public function valid()
  287.             {
  288.                 return $this->getGC()->valid();
  289.             }
  290.            
  291.             public function current()
  292.             {
  293.                 return $this->getGC()->current();
  294.             }
  295.            
  296.             public function key()
  297.             {
  298.                 return $this->getGC()->key();
  299.             }
  300.            
  301.             public function prev()
  302.             {
  303.                 return $this->getGC()->prev();
  304.             }
  305.            
  306.             public function next()
  307.             {
  308.                 return $this->getGC()->next();
  309.             }
  310.            
  311.             public function count()
  312.             {
  313.                 return $this->getGC()->count();
  314.             }
  315.            
  316.             public function keys()
  317.             {
  318.                 return $this->getGC()->keys();
  319.             }
  320.            
  321.             public function values()
  322.             {
  323.                 return $this->getGC()->values();
  324.             }
  325.             #::
  326.         #::
  327.     }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement