X-Git-Url: https://git.mxchange.org/?p=core.git;a=blobdiff_plain;f=framework%2Fmain%2Fclasses%2Fstacker%2Fclass_BaseStacker.php;h=93344d1d2178a304839cf12408c448fd5dce60c0;hp=d6d627ca19131d7eedb1b565c6853770fb19e787;hb=HEAD;hpb=a60894f1d6ef33613d2d0351075aa07aa257f304 diff --git a/framework/main/classes/stacker/class_BaseStacker.php b/framework/main/classes/stacker/class_BaseStacker.php index d6d627ca..cdfa4bc4 100644 --- a/framework/main/classes/stacker/class_BaseStacker.php +++ b/framework/main/classes/stacker/class_BaseStacker.php @@ -1,16 +1,22 @@ * @version 0.0.0 - * @copyright Copyright (c) 2007, 2008 Roland Haeder, 2009 - 2017 Core Developer Team + * @copyright Copyright (c) 2007, 2008 Roland Haeder, 2009 - 2023 Core Developer Team * @license GNU GPL 3.0 or any newer version * @link http://www.shipsimu.org * @@ -28,11 +34,11 @@ use Org\Mxchange\CoreFramework\Object\BaseFrameworkSystem; * along with this program. If not, see . */ abstract class BaseStacker extends BaseFrameworkSystem { - // Exception codes - const EXCEPTION_STACKER_ALREADY_INITIALIZED = 0x050; - const EXCEPTION_STACKER_IS_FULL = 0x051; - const EXCEPTION_NO_STACKER_FOUND = 0x052; - const EXCEPTION_STACKER_IS_EMPTY = 0x053; + /** + * Array "caches" configuration entries for saving "expensive" method + * invocations + */ + private $cachedMaxStackSizes = []; /** * Protected constructor @@ -40,7 +46,7 @@ abstract class BaseStacker extends BaseFrameworkSystem { * @param $className Name of the class * @return void */ - protected function __construct ($className) { + protected function __construct (string $className) { // Call parent constructor parent::__construct($className); } @@ -51,30 +57,51 @@ abstract class BaseStacker extends BaseFrameworkSystem { * @param $stackerName Name of the stack * @param $forceReInit Force re-initialization * @return void - * @throws AlreadyInitializedStackerException If the stack is already initialized + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If the stack is already initialized */ - public function initStack ($stackerName, $forceReInit = false) { - // Is the stack already initialized? - if (($forceReInit === false) && ($this->isStackInitialized($stackerName))) { + public function initStack (string $stackerName, bool $forceReInit = false) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s,forceReInit=%d - CALLED!', $stackerName, intval($forceReInit))); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (($forceReInit === false) && ($this->isStackInitialized($stackerName))) { // Then throw the exception - throw new AlreadyInitializedStackerException(array($this, $stackerName, $forceReInit), self::EXCEPTION_STACKER_ALREADY_INITIALIZED); - } // END - if + throw new BadMethodCallException(array($this, $stackerName, $forceReInit), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); + } - // Initialize the given stack + // Initialize the given stack and "cache" configuration entry $this->initGenericArrayKey('stacks', $stackerName, 'entries', $forceReInit); + $this->cachedMaxStackSizes[$stackerName] = FrameworkBootstrap::getConfigurationInstance()->getConfigEntry(sprintf('stacker_%s_max_size', $stackerName)); + + // Trace message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('BASE-STACKER: EXIT!'); } /** * Initializes all stacks * * @return void + * @throws InvalidArgumentException If a parameter is invalid */ - public function initStacks (array $stacks, $forceReInit = false) { + public function initStacks (array $stacks, bool $forceReInit = false) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stacks()=%d,forceReInit=%d - CALLED!', count($stacks), intval($forceReInit))); + if (count($stacks) == 0) { + // No empty stack name + throw new InvalidArgumentException('Array "stacks" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } + // "Walk" through all (more will be added as needed foreach ($stacks as $stackerName) { // Init this stack + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: Invoking this->initStack(%s,%d) ...', $stackerName, intval($forceReInit))); $this->initStack($stackerName, $forceReInit); - } // END - foreach + } + + // Trace message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('BASE-STACKER: EXIT!'); } /** @@ -82,12 +109,21 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $isInitialized Whether the stack is initialized + * @throws InvalidArgumentException If a parameter is invalid */ - public function isStackInitialized ($stackerName) { + public function isStackInitialized (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } + // Is is there? $isInitialized = ($this->isValidGenericArrayKey('stacks', $stackerName, 'entries')); // Return result + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: isInitialized=%d - EXIT!', intval($isInitialized))); return $isInitialized; } @@ -96,19 +132,25 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $isFull Whether the stack is full - * @throws NoStackerException If given stack is missing + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If given stack is missing */ - protected function isStackFull ($stackerName) { - // Is the stack not yet initialized? - if (!$this->isStackInitialized($stackerName)) { + protected function isStackFull (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); - } // END - if + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); + } // So, is the stack full? - $isFull = (($this->getStackCount($stackerName)) == $this->getConfigInstance()->getConfigEntry('stacker_' . $stackerName . '_max_size')); + $isFull = (($this->getStackCount($stackerName)) == $this->cachedMaxStackSizes[$stackerName]); // Return result + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: isFull=%d - EXIT!', intval($isFull))); return $isFull; } @@ -117,19 +159,25 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $isEmpty Whether the stack is empty - * @throws NoStackerException If given stack is missing + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If given stack is missing */ - public function isStackEmpty ($stackerName) { - // Is the stack not yet initialized? - if (!$this->isStackInitialized($stackerName)) { + public function isStackEmpty (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); - } // END - if + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); + } // So, is the stack empty? $isEmpty = (($this->getStackCount($stackerName)) == 0); // Return result + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: isEmpty=%d - EXIT!', intval($isEmpty))); return $isEmpty; } @@ -138,19 +186,25 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $count Size of stack (array count) - * @throws NoStackerException If given stack is missing + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If given stack is missing */ - public function getStackCount ($stackerName) { - // Is the stack not yet initialized? - if (!$this->isStackInitialized($stackerName)) { + public function getStackCount (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); - } // END - if + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); + } // Now, count the array of entries $count = $this->countGenericArrayElements('stacks', $stackerName, 'entries'); // Return result + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: count=%d - EXIT!', $count)); return $count; } @@ -160,20 +214,29 @@ abstract class BaseStacker extends BaseFrameworkSystem { * @param $stackerName Name of the stack * @param $value Value to add to this stacker * @return void + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If given stack is missing * @throws FullStackerException Thrown if the stack is full */ - protected function addValue ($stackerName, $value) { - // Is the stack not yet initialized or full? - if (!$this->isStackInitialized($stackerName)) { - // Then do it here - $this->initStack($stackerName); + protected function addValueToStack (string $stackerName, $value) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s,value[]=%s - CALLED!', $stackerName, gettype($value))); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { + // Throw an exception + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } elseif ($this->isStackFull($stackerName)) { // Stacker is full - throw new FullStackerException(array($this, $stackerName, $value), self::EXCEPTION_STACKER_IS_FULL); + throw new BadMethodCallException(sprintf('stackerName=%s is full but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } // Now add the value to the stack $this->pushValueToGenericArrayKey('stacks', $stackerName, 'entries', $value); + + // Trace message + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput('BASE-STACKER: EXIT!'); } /** @@ -181,23 +244,32 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $value Value of last added value - * @throws NoStackerException If the named stacker was not found - * @throws EmptyStackerException If the named stacker is empty + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If the named stacker was not found + * @throws BadMethodCallException If the named stacker is empty */ - protected function getLastValue ($stackerName) { - // Is the stack not yet initialized or full? - if (!$this->isStackInitialized($stackerName)) { + protected function getLastValue (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } elseif ($this->isStackEmpty($stackerName)) { // Throw an exception - throw new EmptyStackerException(array($this, $stackerName), self::EXCEPTION_STACKER_IS_EMPTY); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } + // Calculate last index + $lastIndex = $this->getStackCount($stackerName) - 1; + // Now get the last value - $value = $this->getGenericArrayElement('stacks', $stackerName, 'entries', $this->getStackCount($stackerName) - 1); + $value = $this->getGenericArrayElement('stacks', $stackerName, 'entries', $lastIndex); // Return it + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: value[]=%s - EXIT!', gettype($value))); return $value; } @@ -206,23 +278,29 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $value Value of last added value - * @throws NoStackerException If the named stacker was not found - * @throws EmptyStackerException If the named stacker is empty + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If the named stacker was not found + * @throws BadMethodCallException If the named stacker is empty */ - protected function getFirstValue ($stackerName) { - // Is the stack not yet initialized or full? - if (!$this->isStackInitialized($stackerName)) { + protected function getFirstValue (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } elseif ($this->isStackEmpty($stackerName)) { // Throw an exception - throw new EmptyStackerException(array($this, $stackerName), self::EXCEPTION_STACKER_IS_EMPTY); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } // Now get the first value - $value = $this->getGenericArrayElement('stacks', $stackerName, 'entries', 0); + $value = $this->getGenericArrayElement('stacks', $stackerName, 'entries', '0'); // Return it + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: value[]=%s - EXIT!', gettype($value))); return $value; } @@ -231,21 +309,30 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $value Value "poped" from array - * @throws NoStackerException If the named stacker was not found - * @throws EmptyStackerException If the named stacker is empty + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If the named stacker was not found + * @throws BadMethodCallException If the named stacker is empty */ - protected function popLast ($stackerName) { - // Is the stack not yet initialized or full? - if (!$this->isStackInitialized($stackerName)) { + protected function popLast (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } elseif ($this->isStackEmpty($stackerName)) { // Throw an exception - throw new EmptyStackerException(array($this, $stackerName), self::EXCEPTION_STACKER_IS_EMPTY); + throw new BadMethodCallException(sprintf('stackerName=%s is empty but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } // Now, remove the last entry, we don't care about the return value here, see elseif() block above - return $this->popGenericArrayElement('stacks', $stackerName, 'entries'); + $value = $this->popGenericArrayElement('stacks', $stackerName, 'entries'); + + // Return it + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: value[]=%s - EXIT!', gettype($value))); + return $value; } /** @@ -253,21 +340,30 @@ abstract class BaseStacker extends BaseFrameworkSystem { * * @param $stackerName Name of the stack * @return $value Value "shifted" from array - * @throws NoStackerException If the named stacker was not found - * @throws EmptyStackerException If the named stacker is empty + * @throws InvalidArgumentException If a parameter is invalid + * @throws BadMethodCallException If the named stacker was not found + * @throws BadMethodCallException If the named stacker is empty */ - protected function popFirst ($stackerName) { - // Is the stack not yet initialized or full? - if (!$this->isStackInitialized($stackerName)) { + protected function popFirst (string $stackerName) { + // Validate parameter + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: stackerName=%s - CALLED!', $stackerName)); + if (empty($stackerName)) { + // No empty stack name + throw new InvalidArgumentException('Parameter "stackerName" is empty', FrameworkInterface::EXCEPTION_INVALID_ARGUMENT); + } elseif (!$this->isStackInitialized($stackerName)) { // Throw an exception - throw new NoStackerException(array($this, $stackerName), self::EXCEPTION_NO_STACKER_FOUND); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } elseif ($this->isStackEmpty($stackerName)) { // Throw an exception - throw new EmptyStackerException(array($this, $stackerName), self::EXCEPTION_STACKER_IS_EMPTY); + throw new BadMethodCallException(sprintf('stackerName=%s not yet initialized but method called.', $stackerName), FrameworkInterface::EXCEPTION_BAD_METHOD_CALL); } // Now, remove the last entry, we don't care about the return value here, see elseif() block above - return $this->shiftGenericArrayElement('stacks', $stackerName, 'entries'); + $value = $this->shiftGenericArrayElement('stacks', $stackerName, 'entries'); + + // Return it + //* NOISY-DEBUG: */ self::createDebugInstance(__CLASS__, __LINE__)->debugOutput(sprintf('BASE-STACKER: value[]=%s - EXIT!', gettype($value))); + return $value; } }