美文网首页PHP是世界上最好的语言
PHP 之 SplObjectStorage对象存储

PHP 之 SplObjectStorage对象存储

作者: Zeaone | 来源:发表于2019-01-23 17:58 被阅读77次

    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 <p>
     * The serialized representation of a storage.
     * </p>
     * @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 <p>
     * The object to look for.
     * </p>
     * @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 <p>
     * The object to associate data with.
     * </p>
     * @param mixed $data [optional] <p>
     * The data to associate with the object.
     * </p>
     * @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 <p>
     * The object to remove.
     * </p>
     * @return void 
     * @since 5.3.0
     */
    public function offsetUnset ($object) {}
    
    /**
     * Returns the data associated with an <type>object</type> //从存储中获得一个对象
     * @link https://php.net/manual/en/splobjectstorage.offsetget.php
     * @param object $object <p>
     * The object to look for.
     * </p>
     * @return mixed The data previously associated with the object in the storage.
     * @since 5.3.0
     */
    public function offsetGet ($object) {}
    

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

    $collection = new Supor\Collection();//假设有一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 <p>
     * The object to add.
     * </p>
     * @param mixed $data [optional] <p>
     * The data to associate with the object.
     * </p>
     * @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 <p>
     * The object to remove.
     * </p>
     * @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 <p>
     * The object to look for.
     * </p>
     * @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 <p>
     * The storage you want to import.
     * </p>
     * @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 <p>
     * The storage containing the elements to remove.
     * </p>
     * @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 <p>
     * The storage containing the elements to retain in the current storage.
     * </p>
     * @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 <p>
     * The data to associate with the current iterator entry.
     * </p>
     * @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  <p>
     * 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 Supor\Collection(['a' => 'aa', 'b' => 'bb']);
    $collection2 = new Supor\Collection(['c' => 'cc', 'd' => 'dd']);
    $collection3 = new Supor\Collection(['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();
    }
    

    代码执行结果如下:


    执行结果

    相关文章

      网友评论

        本文标题:PHP 之 SplObjectStorage对象存储

        本文链接:https://www.haomeiwen.com/subject/nqxsjqtx.html