深入浅出 PHP SPL(PHP 标准库)(转)

2022-10-12,,,

一、什么是spl库?

spl是用于解决典型问题(standard problems)的一组接口与类的集合。

此扩展只能在php 5.0以后使用,从php 5.3.0 不再被关闭,会一直有效.成为php内核组件一部份。

spl提供了一组标准数据结构。

 

二、spl如何使用?

1.构建此扩展不需要其他扩展。

更详细的情况可参考 

双向链表

双链表是一种重要的线性存储结构,对于双链表中的每个节点,不仅仅存储自己的信息,还要保存前驱和后继节点的地址。

spldoublylinkedlist

  • splstack(栈)

  • splqueue(队列)

 

spldoublylinkedlist implements iterator , arrayaccess , countable {    /* 方法 */
    public __construct ( void )    
    public void add ( mixed $index , mixed $newval )    
    public mixed bottom ( void )//双链表的尾部节点
    public int count ( void )//双联表元素的个数
    public mixed current ( void )//当前记录
    public int getiteratormode ( void ) //获取迭代模式
    public bool isempty ( void )//检测双链表是否为空
    public mixed key ( void )//当前节点索引
    public void next ( void )//移到下条记录
    public bool offsetexists ( mixed $index )//指定index处节点是否存在
    public mixed offsetget ( mixed $index )//获取指定index处节点值
    public void offsetset ( mixed $index , mixed $newval )//设置指定index处值
    public void offsetunset ( mixed $index )//删除指定index处节点
    public mixed pop ( void )//从双链表的尾部弹出元素
    public void prev ( void )//移到上条记录
    public void push ( mixed $value )//添加元素到双链表的尾部
    public void rewind ( void )//将指针指向迭代开始处
    public string serialize ( void )//序列化存储
    public void setiteratormode ( int $mode )//设置迭代模式
    public mixed shift ( void )//双链表的头部移除元素
    public mixed top ( void )//双链表的头部节点
    public void unserialize ( string $serialized )//反序列化
    public void unshift ( mixed $value )//双链表的头部添加元素
    public bool valid ( void )//检查双链表是否还有节点
}

 

  接下来是使用方法:

$list = new spldoublylinkedlist();
$list->push('a');
$list->push('b');
$list->push('c');
$list->push('d');
 
$list->unshift('top');
$list->shift();
 
$list->rewind();//rewind操作用于把节点指针指向bottom所在的节点
echo 'curren node:'.$list->current()."<br />";//获取当前节点
 
$list->next();//指针指向下一个节点
echo 'next node:'.$list->current()."<br />";
 
$list->next();
$list->next();
$list->prev();//指针指向上一个节点
echo 'next node:'.$list->current()."<br />";
 
if($list->current())
    echo 'current node is valid<br />';
else
    echo 'current node is invalid<br />';
     
if($list->valid())//如果当前节点是有效节点,valid返回true
    echo "valid list<br />";
else
  echo "invalid list <br />";
 
var_dump(array(
    'pop' => $list->pop(),
    'count' => $list->count(),    
    'isempty' => $list->isempty(),    
    'bottom' => $list->bottom(),    
    'top' => $list->top()
));
 
$list->setiteratormode(spldoublylinkedlist::it_mode_fifo);
var_dump($list->getiteratormode());
 
for($list->rewind(); $list->valid(); $list->next()){
    echo $list->current().php_eol;
}
 
var_dump($a = $list->serialize());
//print_r($list->unserialize($a));
 
$list->offsetset(0,'new one');
$list->offsetunset(0);
var_dump(array(
    'offsetexists' => $list->offsetexists(4),    
    'offsetget' => $list->offsetget(0),
));
var_dump($list);
 
//堆栈,先进后出
$stack = new splstack();//继承自spldoublylinkedlist类
 
$stack->push("a<br />");
$stack->push("b<br />");
 
echo $stack->pop();
echo $stack->pop();
echo $stack->offsetset(0,'b');//堆栈的offset=0是top所在的位置,offset=1是top位置节点靠近bottom位置的相邻节点,以此类推
 
$stack->rewind();//双向链表的rewind和堆栈的rewind相反,堆栈的rewind使得当前指针指向top所在的位置,而双向链表调用之后指向bottom所在位置
echo 'current:'.$stack->current().'<br />';
$stack->next();//堆栈的next操作使指针指向靠近bottom位置的下一个节点,而双向链表是靠近top的下一个节点
echo 'current:'.$stack->current().'<br />';
echo '<br /><br />';
 
//队列,先进先出
$queue = new splqueue();//继承自spldoublylinkedlist类
$queue->enqueue("a<br />");//插入一个节点到队列里面的top位置
$queue->enqueue("b<br />");
$queue->offsetset(0,'a');//堆栈的offset=0是top所在的位置,offset=1是top位置节点靠近bottom位置的相邻节点,以此类推
echo $queue->dequeue();
echo $queue->dequeue();
echo "<br /><br />";

 

堆(heap)就是为了实现优先队列而设计的一种数据结构,它是通过构造二叉堆(二叉树的一种)实现。根节点最大的堆叫做最大堆或大根堆(splmaxheap),根节点最小的堆叫做最小堆或小根堆(splminheap)。二叉堆还常用于排序(堆排序)

  • splheap

    • splmaxheap

    • splminheap

  • splpriorityqueue

abstract splheap implements iterator , countable {    
    /* 方法 用法同双向链表一致 */
    public __construct ( void )    
    abstract protected int compare ( mixed $value1 , mixed $value2 )    
    public int count ( void )    
    public mixed current ( void )    
    public mixed extract ( void )    
    public void insert ( mixed $value )    
    public bool isempty ( void )    
    public mixed key ( void )    
    public void next ( void )    
    public void recoverfromcorruption ( void )    
    public void rewind ( void )    
    public mixed top ( void )    
    public bool valid ( void )
}

 

使用方法:

//堆
class mysplheap extends splheap{
    //compare()方法用来比较两个元素的大小,绝对他们在堆中的位置
    public function compare( $value1, $value2 ) {
        return ( $value1 - $value2 );
        }
}
 
$obj = new mysplheap();
$obj->insert(0);
$obj->insert(1);
$obj->insert(2);
$obj->insert(3);
$obj->insert(4);
echo $obj->top();//4
echo $obj->count();//5
 
foreach ($obj as $item) {
    echo $item."<br />";
}

阵列 

优先队列也是非常实用的一种数据结构,可以通过加权对值进行排序,由于排序在php内部实现,业务代码中将精简不少而且更高效。通过splpriorityqueue::setextractflags(int  $flag)设置提取方式可以提取数据(等同最大堆)、优先级、和两者都提取的方式。

  • splfixedarray

splfixedarray implements iterator , arrayaccess , countable {
  /* 方法 */  
  public __construct ([ int $size = 0 ] )
  public int count ( void )
  public mixed current ( void )
  public static splfixedarray fromarray ( array $array [, bool $save_indexes = true ] )
  public int getsize ( void )
  public int key ( void )
  public void next ( void )
  public bool offsetexists ( int $index )
  public mixed offsetget ( int $index )
  public void offsetset ( int $index , mixed $newval )
  public void offsetunset ( int $index )
  public void rewind ( void )
  public int setsize ( int $size )
  public array toarray ( void )
  public bool valid ( void )
  public void __wakeup ( void )
}

 

使用方法: 

$arr = new splfixedarray(4);
$arr[0] = 'php';
$arr[1] = 1;
$arr[3] = 'python';//遍历, $arr[2] 为null
foreach($arr as $v) {
    echo $v . php_eol;
}
 
//获取数组长度
echo $arr->getsize(); //4
 
//增加数组长度
$arr->setsize(5);
$arr[4] = 'new one';
 
//捕获异常
try{
    echo $arr[10];
} catch (runtimeexception $e) {
    echo $e->getmessage();
}

 


映射
 

用来存储一组对象的,特别是当你需要唯一标识对象的时候。

  • splobjectstorage

splobjectstorage implements countable , iterator , serializable , arrayaccess {
  /* 方法 */  
  public void addall ( splobjectstorage $storage )
  public void attach ( object $object [, mixed $data = null ] )
  public bool contains ( object $object )
  public int count ( void )
  public object current ( void )
  public void detach ( object $object )
  public string gethash ( object $object )
  public mixed getinfo ( void )
  public int key ( void )
  public void next ( void )
  public bool offsetexists ( object $object )
  public mixed offsetget ( object $object )
  public void offsetset ( object $object [, mixed $data = null ] )
  public void offsetunset ( object $object )
  public void removeall ( splobjectstorage $storage )
  public void removeallexcept ( splobjectstorage $storage )
  public void rewind ( void )
  public string serialize ( void )
  public void setinfo ( mixed $data )
  public void unserialize ( string $serialized )
  public bool valid ( void )
}

 

使用方法: 

class a {
    public $i;    
    public function __construct($i) {
        $this->i = $i;
    }
} 
 
$a1 = new a(1);
$a2 = new a(2);
$a3 = new a(3);
$a4 = new a(4); 
 
$container = new splobjectstorage(); 
 
//splobjectstorage::attach 添加对象到storage中
$container->attach($a1);
$container->attach($a2);
$container->attach($a3); 
 
//splobjectstorage::detach 将对象从storage中移除
$container->detach($a2); 
 
//splobjectstorage::contains用于检查对象是否存在storage中
var_dump($container->contains($a1)); //true
var_dump($container->contains($a4)); //false
 
//遍历
$container->rewind();
while($container->valid()) {
    var_dump($container->current());    
    $container->next();
}

 

原文地址:

《深入浅出 PHP SPL(PHP 标准库)(转).doc》

下载本文的Word格式文档,以方便收藏与打印。