资讯专栏INFORMATION COLUMN

PHP 之 SplObjectStorage对象存储

cpupro / 1044人阅读

摘要:类实现了对象存储映射表,应用于需要唯一标识多个对象的存储场景。在之前仅能存储对象,之后可以针对每个对象添加一条对应的数据。实际上他们并没有直接的关系。

1. 定义

php.net上的定义 The SplObjectStorage class provides a map from objects to data or, by ignoring data, an object set. This dual purpose can be useful in many cases involving the need to uniquely identify objects. 翻译:SplObjectStorage类提供从对象到数据映射功能,或者,通过忽视数据来提供对象集合,在很多涉及需要唯一对象的许多情况下,这两点是十分有用的。

SplObjectStorage类实现了对象存储映射表,应用于需要唯一标识多个对象的存储场景。 在PHP5.3.0之前仅能存储对象,之后可以针对每个对象添加一条对应的数据。 SplObjectStorage类的数据存储依赖于PHP的HashTable实现,与传统的使用数组和spl_object_hash函数生成数组key相比, 其直接使用HashTable的实现在性能上有较大的优势。 有一些奇怪的是,在PHP手册中,SplObjectStorage类放在数据结构目录下。 但是他的实现和观察者模式的接口放在同一个文件(ext/spl/spl_observer.c)。 实际上他们并没有直接的关系。《深入理解php内核》
2. 接口说明
class SplObjectStorage implements Countable, Iterator, Serializable, ArrayAccess {
 //省略,下边详细解释以及翻译
}

此类实现了 Countable, Iterator, Serializable, ArrayAccess 四个接口,分别对应统计,迭代,序列化和数组访问,四个接口分别说明如下

2.1 Countable

此接口中只有一方法count(),看SplObjectStorage 类中此方法的说明(源码位置在php.jar/stubs/SPL/SPL_c1.php文件的1979行,可以用phpstorm按住command鼠标左键跳转过去)

/**
 * Returns the number of objects in the storage //返回存储中的对象数量
 * @link https://php.net/manual/en/splobjectstorage.count.php
 * @return int The number of objects in the storage.
 * @since 5.1.0
 */
public function count () {}

翻译注释:Returns the number of objects in the storage //返回存储中的对象数量

2.2 Iterator

接口注释Interface for external iterators or objects that can be iterated 的翻译为外部迭代器或可以迭代的对象的接口,此接口中有5个方法分别如下(对应注释中有翻译)

/**
 * Rewind the iterator to the first storage element //将迭代器回到第一个存储的元素
 * @link https://php.net/manual/en/splobjectstorage.rewind.php
 * @return void 
 * @since 5.1.0
 */
public function rewind () {}

/**
 * Returns if the current iterator entry is valid //返回当前迭代器条目是否有效
 * @link https://php.net/manual/en/splobjectstorage.valid.php
 * @return bool true if the iterator entry is valid, false otherwise.
 * @since 5.1.0
 */
public function valid () {}

/**
 * Returns the index at which the iterator currently is//返回当前迭代对应的索引
 * @link https://php.net/manual/en/splobjectstorage.key.php
 * @return int The index corresponding to the position of the iterator.
 * @since 5.1.0
 */
public function key () {}

/**
 * Returns the current storage entry //返回当前存储的条目
 * @link https://php.net/manual/en/splobjectstorage.current.php
 * @return object The object at the current iterator position.
 * @since 5.1.0
 */
public function current () {}

/**
 * Move to the next entry //移到下一个条目
 * @link https://php.net/manual/en/splobjectstorage.next.php
 * @return void 
 * @since 5.1.0
 */
public function next () {}
2.3 Serializable

接口注释Interface for customized serializing.的翻译为用于自定义序列化的接口,此接口中有2个方法分别如下(对应注释中有翻译)

/**
 * Serializes the storage //序列化存储
 * @link https://php.net/manual/en/splobjectstorage.serialize.php
 * @return string A string representing the storage. //返回表示存储的字符串
 * @since 5.2.2
 */
public function serialize () {}
/**
 * Unserializes a storage from its string representation //从一个字符串表示中对存储反序列化
 * @link https://php.net/manual/en/splobjectstorage.unserialize.php
 * @param string $serialized 

* The serialized representation of a storage. *

* @return void * @since 5.2.2 */ public function unserialize ($serialized) {}
2.4 ArrayAccess

接口注释Interface to provide accessing objects as arrays.的翻译为提供像访问数组一样访问对象的接口,此接口中有4个方法分别如下(对应注释中有翻译)

/**
 * Checks whether an object exists in the storage //检查存储中是否存在找个对象
 * @link https://php.net/manual/en/splobjectstorage.offsetexists.php
 * @param object $object 

* The object to look for. *

* @return bool true if the object exists in the storage, * and false otherwise. * @since 5.3.0 */ public function offsetExists ($object) {} /** * Associates data to an object in the storage //给存储中的对象赋值 * @link https://php.net/manual/en/splobjectstorage.offsetset.php * @param object $object

* The object to associate data with. *

* @param mixed $data [optional]

* The data to associate with the object. *

* @return void * @since 5.3.0 */ public function offsetSet ($object, $data = null) {} /** * Removes an object from the storage //从存储中删除一个对象 * @link https://php.net/manual/en/splobjectstorage.offsetunset.php * @param object $object

* The object to remove. *

* @return void * @since 5.3.0 */ public function offsetUnset ($object) {} /** * Returns the data associated with an object //从存储中获得一个对象 * @link https://php.net/manual/en/splobjectstorage.offsetget.php * @param object $object

* The object to look for. *

* @return mixed The data previously associated with the object in the storage. * @since 5.3.0 */ public function offsetGet ($object) {}

此接口的功能用代码简单说明如下

$collection = new SuporCollection();//假设有一Collection类,并且已经实现了ArrayAccess 接口
$collection["a"] = 10;//我们可以像给数组赋值一样给此对象赋值
var_dump($collection["a"]);//也可以使用取数组值的方法取得对象的属性 而不用 "->"
//输出 int(10)
3. 方法说明

在每个方法的注释中有对应翻译,来说明这个方法的作用

/**
 * Adds an object in the storage //向存储中添加一个对象
 * @link https://php.net/manual/en/splobjectstorage.attach.php
 * @param object $object 

* The object to add. *

* @param mixed $data [optional]

* The data to associate with the object. *

* @return void * @since 5.1.0 */ public function attach ($object, $data = null) {} /** * Removes an object from the storage //从存储中删除一个对象 * @link https://php.net/manual/en/splobjectstorage.detach.php * @param object $object

* The object to remove. *

* @return void * @since 5.1.0 */ public function detach ($object) {} /** * Checks if the storage contains a specific object //检查存储中是否包含特定的对象 * @link https://php.net/manual/en/splobjectstorage.contains.php * @param object $object

* The object to look for. *

* @return bool true if the object is in the storage, false otherwise. * @since 5.1.0 */ public function contains ($object) {} /** * Adds all objects from another storage //添加一个存储中所有对象 * @link https://php.net/manual/en/splobjectstorage.addall.php * @param SplObjectStorage $storage

* The storage you want to import. *

* @return void * @since 5.3.0 */ public function addAll ($storage) {} /** * Removes objects contained in another storage from the current storage //从当前存储中删除另一个存储中包含的对象 * @link https://php.net/manual/en/splobjectstorage.removeall.php * @param SplObjectStorage $storage

* The storage containing the elements to remove. *

* @return void * @since 5.3.0 */ public function removeAll ($storage) {} /** *从当前存储中删除另一个存储中不包含的对象 * Removes all objects except for those contained in another storage from the current storage * @link https://php.net/manual/en/splobjectstorage.removeallexcept.php * @param SplObjectStorage $storage

* The storage containing the elements to retain in the current storage. *

* @return void * @since 5.3.6 */ public function removeAllExcept ($storage) {} /** * Returns the data associated with the current iterator entry //返回当前迭代器条目相关的数据 * @link https://php.net/manual/en/splobjectstorage.getinfo.php * @return mixed The data associated with the current iterator position. * @since 5.3.0 */ public function getInfo () {} /** * Sets the data associated with the current iterator entry//设置当前迭代器条目相关的数据 * @link https://php.net/manual/en/splobjectstorage.setinfo.php * @param mixed $data

* The data to associate with the current iterator entry. *

* @return void * @since 5.3.0 */ public function setInfo ($data) {} /** * Calculate a unique identifier for the contained objects //给包含的对象计算一个唯一ID * @link https://php.net/manual/en/splobjectstorage.gethash.php * @param $object

* object whose identifier is to be calculated. * @return string A string with the calculated identifier. * @since 5.4.0 */ public function getHash($object) {}

4. 使用

SplObjectStorage的对象操作

//假设有三个Collection对象
$collection1 = new SuporCollection(["a" => "aa", "b" => "bb"]);
$collection2 = new SuporCollection(["c" => "cc", "d" => "dd"]);
$collection3 = new SuporCollection(["e" => "ee", "f" => "ff"]);

$splStorage = new SplObjectStorage();
$splStorage->attach($collection1);
//传入相同的对象会被替代
$splStorage->attach($collection1);
$splStorage->attach($collection2);
$splStorage->attach($collection3);

//统计$splStorage中有多少个对象
$count = $splStorage->count();
var_dump($count);
//得到某一对象的哈希值
$hash1 = $splStorage->getHash($collection1);
var_dump($hash1);

//检查存储中是否包含$collection3
$contains3 = $splStorage->contains($collection3);
var_dump($contains3);

//将指针后移
$splStorage->next();
//读取移动后的key
$key = $splStorage->key();
var_dump($key);

//删除某个对象
$splStorage->detach($collection3);
//统计删除后的数量
$count = $splStorage->count();
var_dump($count);

//遍历$splStorage所有对象
//遍历前先重置一下指针
$splStorage->rewind();
//当当前迭代器条目返回真时
while ($splStorage->valid()) {
    //打印当前条目
    var_dump($splStorage->current());
    //指针后移
    $splStorage->next();
}

代码执行结果如下:

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/30031.html

相关文章

  • 【SPL标准库专题(10)】Datastructures:SplObjectStorage

    摘要:是用来存储一组对象的,特别是当你需要唯一标识对象的时候。类实现了四个接口。可实现统计迭代序列化数组式访问等功能。 PHP SPL SplObjectStorage是用来存储一组对象的,特别是当你需要唯一标识对象的时候。PHP SPL SplObjectStorage类实现了Countable,Iterator,Serializable,ArrayAccess四个接口。可实现统计、迭代、...

    ConardLi 评论0 收藏0
  • PHP - Pimple 源码笔记(上)

    摘要:也就是闲时为了写文章而写的一篇关于源码的阅读笔记。是标准库的缩写,一组旨在解决标准问题的接口和类的集合。提供了一套标准的数据结构,一组遍历对象的迭代器,一组接口,一组标准的异常,一系列用于处理文件的类,提供了一组函数,具体可以查看文档。 也就是闲时为了写文章而写的一篇关于 Pimple 源码的阅读笔记。Pimple 代码有两种编码方式,一种是以 PHP 编写的,另一种是以 C 扩展编写...

    cfanr 评论0 收藏0
  • PHP设计模式——观察者模式

    摘要:设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有订阅对象都能得到通知。类与观察者设计模式没有内在的关系,不过通过它其内置的和方法可以很方便的将观察者实例与一个主题实例相关联以及解除关联。 前言 知识就是作为观察者所获得的结论,经过科学培训的观察者会为我们提供所有能感知的现实。设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有...

    KoreyLee 评论0 收藏0
  • PHP设计模式——观察者模式

    摘要:设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有订阅对象都能得到通知。类与观察者设计模式没有内在的关系,不过通过它其内置的和方法可以很方便的将观察者实例与一个主题实例相关联以及解除关联。 前言 知识就是作为观察者所获得的结论,经过科学培训的观察者会为我们提供所有能感知的现实。设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有...

    lifefriend_007 评论0 收藏0
  • PHP设计模式——观察者模式

    摘要:设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有订阅对象都能得到通知。类与观察者设计模式没有内在的关系,不过通过它其内置的和方法可以很方便的将观察者实例与一个主题实例相关联以及解除关联。 前言 知识就是作为观察者所获得的结论,经过科学培训的观察者会为我们提供所有能感知的现实。设计观察者模式是为了让一个对象跟踪某个状态,知道状态何时改变,一旦状态改变,所有...

    Barrior 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<