SPL基础接口
Iterator 迭代器接口
SPL规定,所有实现了Iterator接口的class,都可以用在foreach Loop中。Iterator接口中包含5个必须实现的方法:
interface Iterator extends Traversable{
//返回当前元素
public mixed current ( void );
//返回当前元素的键
public scalar key ( void );
//向前移动到下一个元素
public void next ( void );
//返回到迭代器的第一个元素
public void rewind ( void );
//检查当前位置是否有效
public boolean valid ( void );
}
示例:
class MyIterator implements Iterator
{
private $position = 0;
private $array = array(
"firstelement",
"secondelement",
"lastelement",
);
function rewind() {
var_dump(__METHOD__);
$this->position = 0;
}
function current() {
var_dump(__METHOD__);
return $this->array[$this->position];
}
function key() {
var_dump(__METHOD__);
return $this->position;
}
function next() {
var_dump(__METHOD__);
++$this->position;
}
function valid() {
var_dump(__METHOD__);
return isset($this->array[$this->position]);
}
}
$it = new MyIterator;
foreach($it as $key => $value) {
var_dump($key, $value);
echo "\n";
}
ArrayAccess 数组式访问接口
实现ArrayAccess接口,可以使得object像array那样操作。ArrayAccess接口包含四个必须实现的方法:
interface ArrayAccess {
//检查一个偏移位置是否存在
public mixed offsetExists ( mixed $offset );
//获取一个偏移位置的值
public mixed offsetGet( mixed $offset );
//设置一个偏移位置的值
public mixed offsetSet ( mixed $offset );
//复位一个偏移位置的值
public mixed offsetUnset ( mixed $offset );
}
示例:
class obj implements arrayaccess {
private $container = array();
public function __construct() {
$this->container = array(
"one" => 1,
"two" => 2,
"three" => 3,
);
}
public function offsetSet($offset, $value) {
if (is_null($offset)) {
$this->container[] = $value;
} else {
$this->container[$offset] = $value;
}
}
public function offsetExists($offset) {
return isset($this->container[$offset]);
}
public function offsetUnset($offset) {
unset($this->container[$offset]);
}
public function offsetGet($offset) {
return isset($this->container[$offset]) ? $this->container[$offset] : null;
}
}
$obj = new obj;
var_dump($obj);exit;
var_dump(isset($obj["two"]));
var_dump($obj["two"]);
unset($obj["two"]);
var_dump(isset($obj["two"]));
$obj["two"] = "A value";
var_dump($obj["two"]);
$obj[] = 'Append 1';
$obj[] = 'Append 2';
$obj[] = 'Append 3';
print_r($obj);
IteratorAggregate 聚合式迭代器接口
假设对象A实现了上面的ArrayAccess接口,这时候虽然可以像数组那样操作,却无法使用foreach遍历,除非实现了前面提到的Iterator接口。
另一个解决方法是,有时会需要将数据和遍历部分分开,这时就可以实现IteratorAggregate接口。它规定了一个getIterator()方法,返回一个使用Iterator接口的object。
IteratorAggregate extends Traversable {
/* 获取一个外部迭代器 */
abstract public Traversable getIterator ( void )
}
示例:
<?php
class myData implements IteratorAggregate {
public $property1 = "Public property one";
public $property2 = "Public property two";
public $property3 = "Public property three";
public function __construct() {
$this->property4 = "last property";
}
public function getIterator() {
return new ArrayIterator($this);
}
}
$obj = new myData;
foreach($obj as $key => $value) {
var_dump($key, $value);
echo "\n";
}
?>
注意:
虽然都继承自Traversable,但这是一个无法在 PHP 脚本中实现的内部引擎接口。我们直接使用IteratorAggregate 或 Iterator 接口来代替它。
RecursiveIterator
- 可以对多层结构的迭代器进行迭代,比如遍历一棵树
- 所有具有层次结构特点的数据都可以用这个接口遍历,如文件夹
- 关键方法
- hasChildren方法可以用于判断当前节点是否存在子节点
- getChildren方法用于得到当前节点子节点的迭代器
- SPL中实现该接口的类
- RecursiveArrayIterator,RecuriveCachingIterator等以Recurive开头的类都可以进行多层次结构化遍历
这个接口用于遍历多层数据,它继承了Iterator接口,因而也具有标准的current()、key()、next()、 rewind()和valid()方法。同时,它自己还规定了getChildren()和hasChildren()方法。The getChildren() method must return an object that implements RecursiveIterator。
SeekableIterator
- SeekableIterator
- 可以通过seek方法定位到集合里面的某个特定的元素
- seek方法的参数是元素的位置,从0开始计算
- SPL中实现该接口的类
- ArrayIterator、DirectoryIterator、FilesystemIterator、GlobIterator、RecursiveArrayIterator、RecursiveDirectoryIterator
SeekableIterator接口也是Iterator接口的延伸,除了Iterator的5个方法以外,还规定了seek()方法,参数是元素的位置,返回该元素。如果该位置不存在,则抛出OutOfBoundsException。
Countable
这个接口规定了一个count()方法,返回结果集的数量。
<?php
//Example One, BAD
class CountMe
{
protected $_myCount = 3;
public function count()
{
return $this->_myCount;
}
}
$countable = new CountMe();
echo count($countable); //result is "1", not as expected
echo $countable->count;//result is "3"
//Example Two, GOOD
class CountMe implements Countable
{
protected $_myCount = 3;
public function count()
{
return $this->_myCount;
}
}
$countable = new CountMe();
echo $countable->count();//result is "3"
echo count($countable); //result is "3" as expected
?>
OuterIterator 迭代器接口
- OuterIterator如果想对迭代器进行一定的处理之后再返回,可以用这个接口
- IteratorIterator类是OuterIterator的实现,扩展的时候可以直接继承IteratorIterator
<?php
/**
*
*/
class outerImpl extends IteratorIterator
{
public function current()
{
# code...
return parent::current().'_tail';
}
public function key()
{
return 'pre_'.parent::key();
}
}
$array = ['value1','value2','value3','value4'];
$outerObj = new outerImpl(new ArrayIterator($array));
foreach ($outerObj as $key => $value) {
# code...
echo '++'.$key.'-'.$value.PHP_EOL;
}
SPL基础接口的更多相关文章
- MMORPG大型游戏设计与开发(服务器 AI 基础接口)
一个模块都往往需要统一的接口支持,特别是对于非常大型的模块,基础结构的统一性非常重要,它往往决定了其扩展对象的通用性.昨天说了AI的基本概述以及组成,作为与场景模块中核心一样重要的地位,基础部分的设计 ...
- .net微信公众号开发——基础接口
作者:王先荣 本文讲述微信公众号开发中基础接口的使用,包括以下内容: (1)获取许可令牌(AccessToken): (2)获取微信服务器地址: (3)上传.下载多媒体文件: ...
- php获取微信基础接口凭证Access_token
php获取微信基础接口凭证Access_token的具体代码,供大家参考,具体内容如下 access_token是公众号的全局唯一票据,公众号调用各接口时都需使用access_token.开发者需要进 ...
- face_recognition 基础接口
face_recognition 基础接口 face_recognition使用世界上最简单的人脸识别库,在Python或命令行中识别和操作人脸. 使用dlib最先进的人脸识别技术构建而成,并具有深度 ...
- ABP开发框架前后端开发系列---(6)ABP基础接口处理和省份城市行政区管理模块的开发
最近没有更新ABP框架的相关文章,一直在研究和封装相关的接口,总算告一段落,开始继续整理下开发心得.上次我在随笔<ABP开发框架前后端开发系列---(5)Web API调用类在Winform项目 ...
- PHP 面向对对象基础(接口,类)
介绍PHP面向对象的基础知识 1. 接口的定义interface ,类定义class,类支持abstract和final修饰符,abstract修饰为抽象类,抽象类 不支持直接实例化,final修饰的 ...
- Java 基础 接口和多态
接口 接口的概念 接口是功能的集合,同样可看做是一种数据类型,是比抽象类更为抽象的”类”. 接口只描述所应该具备的方法,并没有具体实现,具体的实现由接口的实现类(相当于接口的子类)来完成.这样将功能的 ...
- JDBC的基础接口及其用法
JDBC基础 所谓JDBC即是:Java DataBase Connectivity,java与数据库的连接.是一些用来执行SQL语句的Java API. 我们进行JDBC的编程,主要常用的几个概念: ...
- Python基础-接口与归一化设计、抽象类、继承顺序、子类调用父类,多态与多态性
一.接口与归一化设计 Java接口是一系列方法的声明,是一些方法特征的集合,一个接口只有方法的特征没有方法的实现,因此这些方法可以在不同的地方被不同的类实现,而这些实现可以具有不同的行为(功能). 由 ...
随机推荐
- 命令替换、权限、chmod、特殊权限
命令替换 把字符串里面的命令先执行再把该字符串输出,与PHP的""里面的变量被执行一样. $(COMMAND) `COMMAND` [root@jiakang ~]# echo & ...
- Ansible 配置文件详解
# config file for ansible -- http://ansible.com/ # ============================================== # ...
- PHP的闭包和匿名函数
闭包函数是创建时,封装周围状态的函数,而匿名函数是没有名称的函数,匿名函数可以被赋值给变量,也就是所谓的函数式编程,也可以传递参数,经常作为回调函数.(理论上讲:匿名函数和闭包不算是一个概念,php却 ...
- Ubuntu上安装配置Java环境
参考文献:在Ubuntu 14.04中安装JDK 方法一: @ 安装 1. 添加PPA repository系统 PPA repository介绍 $sudo add-apt-repository p ...
- 图论--Floyd总结
Key word: ①最短路 ②传递闭包:大小关系 数值关系 先后关系 联通关系 ③floyd变形 ④实现方式:插点发法 ⑤思想:动态规划 1.最短路: 最短路 ...
- jenkins 安装成功之后配置
一.基础配置介绍 jenkins安装成功之后如果某些东西配置的话,可能部署的时候一堆的问题,所以单独总结一下,让大家少走弯路 二.准备工作 1.需要准备一台服务器,大家可以在网上买,个人学习的话还是建 ...
- Tomcat Ghostcat - AJP协议漏洞DEBUG
环境 IntelliJ IDEA 2020.1 x64 tomcat-8.5.46 配置 pom.xml <?xml version="1.0" encoding=" ...
- Thinkphp 缓存RCE
5.0.0<=ThinkPHP5<=5.0.10 . 漏洞利用条件: 1.基于tp5开发的代码中使用了Cache::set 进行缓存 2.在利用版本范围内 3.runtime目录可以 ...
- Codeforces Round #577 (Div. 2) D. Treasure Hunting
Codeforces Round #577 (Div. 2) D. Treasure Hunting 这个一场div2 前面三题特别简单,这个D题的dp还是比较难的,不过题目告诉你了只能往上走,所以 ...
- Word转pdf,再转图片插入PDF
WORD转PDF所需jar包: https://yangtaotao.lanzous.com/ice1jlc PDF转图片所需jar包: https://yangtaotao.lanzous.com/ ...