<?php
class Container implements ArrayAccess, Countable, Iterator, JsonSerializable, Serializable
{
protected $values;
public function __construct(... $values)
{
$this->values = [];
foreach ($values as $value) {
if (is_array($value)) {
foreach ($value as $val) {
$this->append($val);
}
}
else {
$this->append($value);
}
}
}
protected function validate($value)
{
return true;
}
protected function format($value)
{
return $value;
}
public function prepend($value)
{
if ($this->validate($value)) {
array_unshift($this->values, $this->format($value));
return true;
}
return false;
}
public function shift()
{
return array_shift($this->values);
}
public function append($value)
{
if ($this->validate($value)) {
array_push($this->values, $this->format($value));
return true;
}
return false;
}
public function pop()
{
return array_pop($this->values);
}
public function toArray()
{
return $this->values;
}
public function filter($callback)
{
$this->values = array_values(array_filter($this->values, $callback));
return $this;
}
public function map($callback)
{
$this->values = array_values(array_map([$this, 'format'], array_filter(array_map($callback, $this->values), [$this, 'validate'])));
return $this;
}
public function offsetExists($offset)
{
return key_exists($offset, $this->values);
}
public function offsetGet($offset)
{
return ($this->offsetExists($offset) ? $this->values[$offset] : null);
}
public function offsetSet($offset, $value)
{
if (is_null($offset)) {
$this->append($value);
return;
}
if (!$this->offsetExists($offset)) {
$cn = get_called_class();
throw new Exception("{$cn} cannot set value at index {$offset}.");
}
if ($this->validate($value)) {
$this->values[$offset] = $this->format($value);
}
}
public function offsetUnset($offset)
{
if ($this->offsetExists($offset)) {
unset($this->values[$offset]);
}
}
public function count()
{
return count($this->values);
}
public function current()
{
return current($this->values);
}
public function key()
{
return key($this->values);
}
public function next()
{
return next($this->values);
}
public function rewind()
{
reset($this->values);
}
public function valid()
{
return !is_null(key($this->values));
}
public function jsonSerialize()
{
return $this->toArray();
}
public function serialize()
{
return serialize($this->values);
}
public function unserialize($data)
{
$this->values = unserialize($data);
}
}
class IntContainer extends Container
{
protected function validate($value)
{
return is_numeric($value);
}
protected function format($value)
{
return intval($value);
}
}
$nums = new IntContainer(2, 4, 6, 8);
var_dump(
$nums->map(function ($num) {
return sprintf("[%'10s]",sprintf("0x%10x",$num + 1));
})
->toArray()
);
Deprecated: Return type of Container::offsetExists($offset) should either be compatible with ArrayAccess::offsetExists(mixed $offset): bool, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 83
Deprecated: Return type of Container::offsetGet($offset) should either be compatible with ArrayAccess::offsetGet(mixed $offset): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 88
Deprecated: Return type of Container::offsetSet($offset, $value) should either be compatible with ArrayAccess::offsetSet(mixed $offset, mixed $value): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 93
Deprecated: Return type of Container::offsetUnset($offset) should either be compatible with ArrayAccess::offsetUnset(mixed $offset): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 110
Deprecated: Return type of Container::count() should either be compatible with Countable::count(): int, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 117
Deprecated: Return type of Container::current() should either be compatible with Iterator::current(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 122
Deprecated: Return type of Container::next() should either be compatible with Iterator::next(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 132
Deprecated: Return type of Container::key() should either be compatible with Iterator::key(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 127
Deprecated: Return type of Container::valid() should either be compatible with Iterator::valid(): bool, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 142
Deprecated: Return type of Container::rewind() should either be compatible with Iterator::rewind(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 137
Deprecated: Return type of Container::jsonSerialize() should either be compatible with JsonSerializable::jsonSerialize(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 147
Deprecated: Container implements the Serializable interface, which is deprecated. Implement __serialize() and __unserialize() instead (or in addition, if support for old PHP versions is necessary) in /in/v80dK on line 3
Deprecated: IntContainer implements the Serializable interface, which is deprecated. Implement __serialize() and __unserialize() instead (or in addition, if support for old PHP versions is necessary) in /in/v80dK on line 163
array(0) {
}
Output for 8.3.5
Warning: PHP Startup: Unable to load dynamic library 'sodium.so' (tried: /usr/lib/php/8.3.5/modules/sodium.so (libsodium.so.23: cannot open shared object file: No such file or directory), /usr/lib/php/8.3.5/modules/sodium.so.so (/usr/lib/php/8.3.5/modules/sodium.so.so: cannot open shared object file: No such file or directory)) in Unknown on line 0
Deprecated: Return type of Container::offsetExists($offset) should either be compatible with ArrayAccess::offsetExists(mixed $offset): bool, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 83
Deprecated: Return type of Container::offsetGet($offset) should either be compatible with ArrayAccess::offsetGet(mixed $offset): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 88
Deprecated: Return type of Container::offsetSet($offset, $value) should either be compatible with ArrayAccess::offsetSet(mixed $offset, mixed $value): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 93
Deprecated: Return type of Container::offsetUnset($offset) should either be compatible with ArrayAccess::offsetUnset(mixed $offset): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 110
Deprecated: Return type of Container::count() should either be compatible with Countable::count(): int, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 117
Deprecated: Return type of Container::current() should either be compatible with Iterator::current(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 122
Deprecated: Return type of Container::next() should either be compatible with Iterator::next(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 132
Deprecated: Return type of Container::key() should either be compatible with Iterator::key(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 127
Deprecated: Return type of Container::valid() should either be compatible with Iterator::valid(): bool, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 142
Deprecated: Return type of Container::rewind() should either be compatible with Iterator::rewind(): void, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 137
Deprecated: Return type of Container::jsonSerialize() should either be compatible with JsonSerializable::jsonSerialize(): mixed, or the #[\ReturnTypeWillChange] attribute should be used to temporarily suppress the notice in /in/v80dK on line 147
Deprecated: Container implements the Serializable interface, which is deprecated. Implement __serialize() and __unserialize() instead (or in addition, if support for old PHP versions is necessary) in /in/v80dK on line 3
Deprecated: IntContainer implements the Serializable interface, which is deprecated. Implement __serialize() and __unserialize() instead (or in addition, if support for old PHP versions is necessary) in /in/v80dK on line 163
array(0) {
}