正文
数据类型
PHP 支持 10 种原始数据类型。
四种标量类型:
bool(布尔型)
int(整型)
float(浮点型,也称作 double)
string(字符串)
四种复合类型:
array(数组)
object(对象)
callable(可调用)
iterable(可迭代)
最后是两种特殊类型:
resource(资源)
NULL(无类型)
可能还会读到一些关于“双精度(double)”类型的参考。实际上 double 和 float 是相同的,由于一些历史的原因,这两个名称同时存在。
变量的类型通常不是由程序员设定的,确切地说,是由 PHP 根据该变量使用的上下文在运行时决定的。
callable
Callback / Callable 类型 ,
一些函数如 call_user_func()
或 usort()
可以接受用户自定义的回调函数作为参数。
回调函数不止可以是简单函数,还可以是对象的方法,包括静态类方法。
回调函数参数中PHP将函数以string形式传递。除了普通的用户自定义函数外,也可传递 匿名函数 给回调参数。
<?php
// An example callback function
function my_callback_function() {
echo 'hello world!';
}
// An example callback method
class MyClass {
static function myCallbackMethod() {
echo 'Hello World!';
}
}
// Type 1: Simple callback
call_user_func('my_callback_function');
// Type 2: Static class method call
call_user_func(array('MyClass', 'myCallbackMethod'));
// Type 3: Object method call
$obj = new MyClass();
call_user_func(array($obj, 'myCallbackMethod'));
// Type 4: Static class method call (As of PHP 5.2.3)
call_user_func('MyClass::myCallbackMethod');
// Type 5: Relative static class method call (As of PHP 5.3.0)
class A {
public static function who() {
echo "A\n";
}
}
class B extends A {
public static function who() {
echo "B\n";
}
}
call_user_func(array('B', 'parent::who')); // A
// Type 6: Objects implementing __invoke can be used as callables (since PHP 5.3)
class C {
public function __invoke($name) {
echo 'Hello ', $name, "\n";
}
}
$c = new C();
call_user_func($c, 'PHP!');
?>
Iterable
Iterable 可迭代对象 是 PHP 7.1 中引入的一个伪类型。 它接受任何 array 或实现了 Traversable 接口的对象。 这些类型都能用 foreach 迭代, 也可以和 生成器 里的 yield from 一起使用。
Iterator(迭代器)接口 ,可在内部迭代自己的外部迭代器或类的接口。
Iterator extends Traversable {
/* 方法 */
abstract public current ( ) : mixed
abstract public key ( ) : scalar
abstract public next ( ) : void
abstract public rewind ( ) : void
abstract public valid ( ) : bool
}
里面 Traversable(遍历)接口 没有任何方法,它的作用仅仅是作为所有可遍历类的基本接口:
Traversable {
}
Iterator::current
— 返回当前元素
Iterator::key
— 返回当前元素的键
Iterator::next
— 向前移动到下一个元素
Iterator::rewind
— 返回到迭代器的第一个元素
Iterator::valid
— 检查当前位置是否有效
foreach
迭代时,先Iterator::rewind
返回到第一个元素,然后Iterator::valid
检查当前位置是否有效,
如果有效,向下 Iterator::key
取键 、 Iterator::current
取值;
接着Iterator::next
向前移动到下一个元素,然后Iterator::valid
检查当前位置是否有效,如果有效,继续循环,如果无效,停止循环。
while
循环时,Iterator::valid
检查当前位置是否有效;如果有效,进入循环,Iterator::key
取键 、 Iterator::current
取值;
接着Iterator::next
向前移动到下一个元素;然后while
继续用条件Iterator::valid
检查当前位置是否有效;
如果有效,继续循环,如果无效,停止循环。
简单迭代控制
<?php
class myIterator implements Iterator
{
private $position = 0;
private $array = array(
"firstelement",
"secondelement",
"lastelement",
);
public function __construct() {
$this->position = 0;
}
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]);
}
}
测试:
<?php
$it = new myIterator;
foreach ($it as $key => $value) {
var_dump($key, $value);
echo "\n";
};
输出:
string(18) "myIterator::rewind"
string(17) "myIterator::valid"
string(19) "myIterator::current"
string(15) "myIterator::key"
int(0)
string(12) "firstelement"
string(16) "myIterator::next"
string(17) "myIterator::valid"
string(19) "myIterator::current"
string(15) "myIterator::key"
int(1)
string(13) "secondelement"
string(16) "myIterator::next"
string(17) "myIterator::valid"
string(19) "myIterator::current"
string(15) "myIterator::key"
int(2)
string(11) "lastelement"
string(16) "myIterator::next"
string(17) "myIterator::valid"
复杂迭代控制
如果数组的键不是连续的数字呢,用上面++
会定位不到,我们可以用数组指针函数reset()
、current()
、key()
、next()
实现:
<?php
class myIterator implements Iterator
{
private $array = array(
"one" => "firstelement",
"two" => "secondelement",
"three" => "lastelement",
);
public function rewind() {
reset($this->array);
}
public function current() {
return current($this->array);
}
public function key() {
return key($this->array);
}
public function next() {
next($this->array);
}
public function valid() {
return isset($this->array[key($this->array)]);
}
}
Resource
Resource 资源类型 资源 resource 是一种特殊变量, 保存了到外部资源的一个引用。资源是通过专门的函数来建立和使用的。 所有这些函数及其相应资源类型见 资源类型列表 。
类型比较
两种比较方式。
松散比较:使用两个等号 == 比较,只比较值,不比较类型。
严格比较:用三个等号 === 比较,除了比较值,也比较类型。
多种类型比较:
常用对照:
看个例子,想想结果。PHP中 比较 0、false、null。这几个还是比较绕的。
<?php
echo '0 == false: ';
var_dump(0 == false);
echo '0 === false: ';
var_dump(0 === false);
echo PHP_EOL;
echo '0 == null: ';
var_dump(0 == null);
echo '0 === null: ';
var_dump(0 === null);
echo PHP_EOL;
echo 'false == null: ';
var_dump(false == null);
echo 'false === null: ';
var_dump(false === null);
echo PHP_EOL;
echo '"0" == false: ';
var_dump("0" == false);
echo '"0" === false: ';
var_dump("0" === false);
echo PHP_EOL;
echo '"0" == null: ';
var_dump("0" == null);
echo '"0" === null: ';
var_dump("0" === null);
echo PHP_EOL;
echo '"" == false: ';
var_dump("" == false);
echo '"" === false: ';
var_dump("" === false);
echo PHP_EOL;
echo '"" == null: ';
var_dump("" == null);
echo '"" == null: ';
var_dump("" === null);
参考资料
PHP 手册 语言参考 类型 https://www.php.net/manual/zh/language.types.php
PHP 数据类型 https://www.runoob.com/php/php-datatypes.html
PHP 类型比较 https://www.runoob.com/php/php-types-comparisons.html
PHP 手册 语言参考 类型 Callback / Callable 类型 https://www.php.net/manual/zh/language.types.callable.php
PHP 手册 语言参考 函数 匿名函数 https://www.php.net/manual/zh/functions.anonymous.php
PHP 手册 语言参考 类型 Iterable 可迭代对象 https://www.php.net/manual/zh/language.types.iterable.php
PHP 手册 语言参考 预定义接口 Iterator(迭代器)接口 https://www.php.net/manual/zh/class.iterator.php
PHP 手册 语言参考 类型 Resource 资源类型 https://www.php.net/manual/zh/language.types.resource.php
PHP 手册 附录 资源类型列表 https://www.php.net/manual/zh/resource.php