基础捡漏:
1、短标记<??> 通过修改ini文件的short_open_tag或编译时 --enable-short-tags 可用 不推荐使用、
2、?>默认有隐藏分号结束,而文件最后可以省略?>
3、使用条件的高级分离术
<?php if ($expression == true): ?>
This will show if the expression is true.
<?php else: ?>
Otherwise this will show.
<?php endif; ?>
!!后面的程序不执行了??
php解析器会在条件未达成时直接跳过该条件语句块??所以比echo、print更有效率
所以适用输出大段文本
4、script式
<script language="php">
echo 'some editors (like FrontPage) don\'t
like processing instructions';
</script>
好像没什么意义阿,又输出不出来
5、自 PHP 5.4 起,短格式的 echo 标记 <?= 总会被识别并且合法,而不管 short_open_tag 的设置是什么。所以1不成立
6、9种原始数据类型
标量类型
boolean
integer
float
string
复合类型
array
object
Callback/Callable(可调用)??与类有关
特殊类型
resource(资源)
NULL(无类型)
为了确保代码的易读性,本手册还介绍了一些伪类型://就是实际没有这种类型
mixed(混合类型)
number(数字类型)
callback(回调类型,又称为 callable)
array|object(数组 | 对象类型)
void (无类型)
7、php是弱类型语言,所以php根据变量的上下文来判断变量的类型;
查看变量的值和类型:var_dump();
输出类型:gettype();
判断是否是某类型:is_int/string/object()
8、变量强制转换为某类型
(boolean/bool) $foo
settype($a, 'string');//返回true/false
9、echo(false);为空白!
10、类型比较表,https://www.php.net/manual/zh/types.comparisons.php 比较很特殊的值
11、空数组转换为boolean时,为false,变量在流程控制中if($a),自动转化为boolean类型
12、整数:要使用八进制表达,数字前必须加上 0(零)。要使用十六进制表达,数字前必须加上 0x。要使用二进制表达,数字前必须加上 0b
13、整数是有符号的,整数的最大最小值与系统有关,32位,0/1 (符号位)31个1 所以是2^31-1 (二进制计算哟) 2147483647
同理64位系统,则是2^63-1 为9223372036854775807
超过这两个数,则将转化成float类型
14、强制转化为整形
(int) 或 (integer)
intval($非object,0/10/2/8/16) object会报错,后面参数为什么进制,如果是0,则根据变量本身来判断
成功时返回 var
的 integer 值,失败时返回 0。 空的 array 返回 0,非空的 array 返回 1
15、浮点数的精度有限。尽管取决于系统,PHP通常使用IEEE 754双精度格式(64位),永远不要相信浮点数结果精确到了最后一位,也永远不要比较两个浮点数是否相等
16、计算浮点数相等的例子
<?php
$a = 1.23456789;
$b = 1.23456780;
$epsilon = 0.00001;
if(abs($a-$b) < $epsilon) {
echo "true";
}
?>
17、NAN is_nan()
18、每个字符等同于一个字节。这意味着 PHP 只能支持 256 的字符集,因此不支持 Unicode,最大可达2GB
19、四种表达方式
单引号
双引号
heredoc 语法结构
nowdoc 语法结构
20、单引号除\' \\外 其他\转义均无效
21、\[0-7]{1,3} 符合该正则表达式序列的是一个以八进制方式来表达的字符
\x[0-9A-Fa-f]{1,2} 符合该正则表达式序列的是一个以十六进制方式来表达的字符
不太明白
22、heredoc 句法结构:<<<
$str = <<<EOD
Example of string
spanning multiple lines
using heredoc syntax.
EOD;
EOD是遵守 PHP 的规则:只能包含字母、数字和下划线,并且必须以字母和下划线作为开头。
echo <<<EOT
My name is "$name". I am printing some $foo->foo.
Now, I am printing some {$foo->bar[1]}.
This should print a capital 'A': \x41
EOT;
里面可以包含变量
Heredoc 结构还可以来初始化静态变量和类的属性和常量
或者
$str = <<<“EOD”
Example of string
spanning multiple lines
using heredoc syntax.
EOD;
23、Nowdoc 结构
$str = <<<‘EOD’
Example of string
spanning multiple lines
using heredoc syntax.
EOD;
里面纯文本,不解析,类似单引号
24、当 PHP 解析器遇到一个美元符号($)时,它会和其它很多解析器一样,去组合尽量多的标识以形成一个合法的变量名。可以用花括号来明确变量名的界线。一个 array 索引或一个 object 属性也可被解析
// Invalid. "s" is a valid character for a variable name, but the variable is $juice.
echo "He drank some juice made of $juices.";
He drank some juice made of .
echo "He drank some $juices[0] juice.".PHP_EOL;
echo "$people->john drank some $juices[0] juice.".PHP_EOL;
25、php换行符PHP_EOL,以提高代码的源代码级可移植性
26、变量解析复杂模式(花括号)
{$} $必须和{紧挨着
// 有效,只有通过花括号语法才能正确解析带引号的键名
echo "This works: {$arr['key']}";
// 有效,输出: This is fantastic
echo "This is ${great}";
echo "This is the value of the var named by the return value of getName(): {${getName()}}";
// 无效,输出: This is the return value of getName(): {getName()}
echo "This is the return value of getName(): {getName()}"
<?php
class beers {
const softdrink = 'rootbeer';
public static $ale = 'ipa';
}
$rootbeer = 'A & W';
$ipa = 'Alexander Keith\'s';
// 有效,输出: I'd like an A & W
echo "I'd like an {${beers::softdrink}}\n";
// 也有效,输出: I'd like an Alexander Keith's
echo "I'd like an {${beers::$ale}}\n";
总结:复杂的起始{${ 表达式,可以是类的变量或者函数}}
27、string 中的字符可以通过一个从 0 开始的下标 类似array
// 取得字符串的第一个字符
$str = 'This is a test.';
$first = $str[0];
string 也可用花括号访问,比如 $str{42}
用超出字符串长度的下标写入将会拉长该字符串并以空格填充,非整数的下标将会转成整数
28、substr(string $string, int $start[, int $length]) : string
length 和 start 可为负 从末尾开始算
substr_replace( mixed $string , mixed $replacement , mixed $start [, mixed $length ] ) : mixed)
length 和 start 可为负 从末尾开始算
29、(string)$var 和 strval() 不能将 strval() 用于数组或对象
30、一个布尔值 boolean 的 TRUE 被转换成 string 的 "1"。Boolean 的 FALSE 被转换成 ""(空字符串)
31、获取类的名称
get_class($object) 和 __toString()
32、大部分的 PHP 值可以转变成 string 来永久保存,这被称作串行化
serialize() 返回字符串,此字符串包含了表示 value
的字节流,可以存储于任何地方。
这有利于存储或传递 PHP 的值,同时不丢失其类型和结构。
想要将已序列化的字符串变回 PHP 的值,可使用 unserialize()
[1,2,3,4] => string(38) "a:4:{i:0;i:1;i:1;i:2;i:2;i:3;i:3;i:4;}"
33、字符串转数值
$foo = 1 + "10.5"; // $foo is float (11.5)
$foo = 1 + "-1.3e3"; // $foo is float (-1299)
$foo = 1 + "bob-1.3e3"; // $foo is integer (1)
$foo = 1 + "bob3"; // $foo is integer (1)
$foo = 1 + "10 Small Pigs"; // $foo is integer (11)
$foo = 4 + "10.2 Little Piggies"; // $foo is float (14.2)
$foo = "10.0 pigs " + 1; // $foo is float (11)
$foo = "10.0 pigs " + 1.0; // $foo is float (11)
33、ord() 查字符的ascii吗
chr()反过来
34、字符串类型详解
PHP 中的 string 的实现方式是一个由字节组成的数组再加上一个整数指明缓冲区长度
NUL 和 NULL
Bin
(二进制)
|
Oct
(八进制)
|
Dec
(十进制)
|
Hex
(十六进制)
|
缩写/字符
|
解释
|
0000 0000
|
00
|
0
|
0x00
|
NUL(null)
|
空字符
|
0000 0001
|
01
|
1
|
0x01
|
SOH(start of headline)
|
标题开始
|
0000 0010
|
02
|
2
|
0x02
|
STX (start of text)
|
正文开始
|
一个‘L’的NUL用于结束一个ASCII字符串,
两个‘L’的NULL用于表示什么也不指向(空指针)
字符串类型的此特性解释了为什么 PHP 中没有单独的“byte”类型 - 已经用字符串来代替了
35、栈(stack)又名堆栈,
它是一种运算受限的线性表。其限制是仅允许在表的一端进行插入和删除运算。这一端被称为栈顶,相对地,把另一端称为栈底。向一个栈插入新元素又称作进栈、入栈或压栈,它是把新元素放到栈顶元素的上面,使之成为新的栈顶元素;从一个栈删除元素又称作出栈或退栈,它是把栈顶元素删除掉,使其相邻的元素成为新的栈顶元素
36、数组
PHP 中的数组实际上是一个有序映射。映射是一种把 values 关联到 keys 的类型。
key 为整数或者字符串
5.4起 可[]定义
布尔值也会被转换成整型。即键名 true 实际会被储存为 1 而键名 false 会被储存为 0。
Null 会被转换为空字符串,即键名 null 实际会被储存为 ""。
亦可用花括号来访问 $array[42] 和 $array{42} $array{“a”}
37、5.4之前不能进行数组解引用
<?php
function getArray() {
return array(1, 2, 3);
}
// on PHP 5.4
$secondElement = getArray()[1];
// previously
$tmp = getArray();
$secondElement = $tmp[1];
// or
list(, $secondElement) = getArray();
list()为一个语言结构,将数组按顺序赋值于变量,7.1.0之后可以用于字符串数组,方向从左到右
38、$arr[] = value;加在末尾
39、删除某键值
unset($arr[5]);
40、array_values ()
返回所有的值,并重建数字索引
$array = array("size" => "XL", "color" => "gold");
print_r(array_values($array));
Array
(
[0] => XL
[1] => gold
)
41、注意这里所使用的最大整数键名不一定当前就在数组中。它只要在上次数组重新生成索引后曾经存在过就行了
比如unset数组的所有元素,但是索引的排序一直都在
42、unset() 函数允许删除数组中的某个键。但要注意数组将不会重建索引
43、
$foo[bar] = 'enemy';
echo $foo[bar];
如之前无常量bar,则php自动转为'bar'; but
this will throw an Error in a future version of PHP
44、尽量不要用常量来做key,因为常量可能随着版本变化而变化,保留字也是一样的
45、转化为数组
(array)$var $var如果是除对象和数组外其他类型,则转为一个只有0索引的数组
null将转成一个空数组
46、对象转成数组
其单元为该对象的属性。键名将为成员变量名,不过有几点例外:整数属性不可访问;私有变量前会加上类名作前缀;保护变量前会加上一个 '*' 做前缀。这些前缀的前后都各有一个 NULL 字符。
class A {
private $A=1; // This will become '\0A\0A'
}
class B extends A {
private $A=2; // This will become '\0B\0A'
public $AA=3; // This will become 'AA'
protected $AAA=4;
}
var_dump((array) new B());
array(3) { ["BA"]=> int(2) ["AA"]=> int(3) ["*AAA"]=> int(4) ["AA"]=> int(1) } 后面的AA 其实是'\0A\0A';
类中函数将会被忽视
47、比较数组
arr_diff(很多array) 返回在第一个数组中但是不在其他 array 里的值
$a = array("a" => "apple", "b" => "banana");
$b = array("a" => "pear", "b" => "strawberry", "c" => "cherry");
$c = $a + $b; // 谁在前,以谁为尊
array(3) {
["a"]=>
string(5) "apple"
["b"]=>
string(6) "banana"
["c"]=>
string(6) "cherry"
}
$c = $b + $a;
array(3) {
["a"]=>
string(4) "pear"
["b"]=>
string(10) "strawberry"
["c"]=>
string(6) "cherry"
}
48、数组传引用,直接改数组值
$colors = array('red', 'blue', 'green', 'yellow');
foreach ($colors as &$color) {
$color = strtoupper($color);
}
var_dump($colors);
array(4) { [0]=> string(3) "RED" [1]=> string(4) "BLUE" [2]=> string(5) "GREEN" [3]=> &string(6) "YELLOW" }之前认为&为bug
在打印之前unset($color),则会解决这个bug
49、填充数组
$handle = opendir('.');//打开读取,关闭,并将文件名写入一个数组
while (false !== ($file = readdir($handle))) {
$files[] = $file;
}
closedir($handle);
50、数组(Array) 的赋值总是会涉及到值的拷贝。使用引用运算符通过引用来拷贝数组。
$arr1 = array(2, 3);
$arr2 = $arr1;
$arr2[] = 4; // $arr2 is changed,
// $arr1 is still array(2, 3)
$arr3 = &$arr1;
$arr3[] = 4; // now $arr1 and $arr3 are the same
51、对象
要创建一个新的对象 object,使用 new 语句实例化一个类。
52、转化为对象
除数组外,如果其它任何类型的值被转换成对象,将会创建一个内置类 stdClass 的实例
var_dump((object)NULL);
var_dump((object)"abc");
object(stdClass)#1 (0) { }
object(stdClass)#1 (1) { ["scalar"]=> string(3) "abc" }
数组转对象
var_dump((object) array('1' => 'foo'));
object(stdClass)#1 (1) { ["1"]=> string(3) "foo" }
$obj = (object) array('1' => 'foo');
var_dump(isset($obj->{'1'}));//注意花括号的使用
53、资源 resource 是一种特殊变量,保存了到外部资源的一个引用
54、null类型 只有一个值null 特殊的 NULL
值表示一个变量没有值
三种情况认定为null
被赋值为 NULL。
尚未被赋值。
被 unset()。
55、转换为null值
使用 (unset) $var 将一个变量转换为 null 将不会删除该变量或 unset 其值。仅是返回 NULL
值而已。
$a = 123;
var_dump((unset)$a);
var_dump($a);
NULL
int(123)
56、call_user_func(funcname, argu1,argu2),把第一个参数作为回调函数调用,后续为该函数的参数,而funcname则为callback类型,实际上是以string形式传递的
57、usort — 使用用户自定义的比较函数对数组中的值进行排序
usort(array &arr, callback): bool
在第一个参数小于,等于或大于第二个参数时,该比较函数必须相应地返回一个小于,等于或大于 0 的整数
callback($a, $b): int
57、Callback / Callable 类型
自 PHP 5.4 起可用 callable 类型指定回调类型 callback
callback 可以使用任何内置或用户自定义的函数,还可以是对象的方法,包括静态类方法,但除了语言结构外
当时对象的方法时,用array做参数
// An example callback method
class MyClass {
static function myCallbackMethod() {
echo 'Hello World!';
}
}
// 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');
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!');
58、魔术函数__invoke
当尝试以调用函数的方式调用一个对象时,__invoke() 方法会被自动调用
class CallableClass
{
function __invoke($x) {
var_dump($x);
}
}
$obj = new CallableClass;
$obj(5);//把object当成函数使用,invoke就被调用了
var_dump(is_callable($obj)); //true
is_callable() 函数用于检测函数在当前环境中是否可调用
59、range()函数
创建一个包含从 "0" 到 "5" 之间的元素范围的数组
$number = range(0,5)
;
print_r ($number);
60、Closure 闭包
闭包就是能够读取其他函数内部变量的函数,所以闭包可以理解成“定义在一个函数内部的函数“。在本质上,闭包是将函数内部和函数外部连接起来的桥梁。
// Our closure
$double = function($a) {
return $a * 2;
};
// This is our range of numbers
$numbers = range(1, 5);
// Use the closure as a callback here to
// double the size of each element in our
// range
$new_numbers = array_map($double, $numbers);//array_map:函数将用户自定义函数作用到数组中的每个值上,并返回用户自定义函数作用后的带有新值的数组
print implode(' ', $new_numbers);
61、call_user_func_array(callable $callback , array $param_arr ) : mixed
第一个参数为回调函数,后面的数组依次为他的参数,如果出错的话返回false
function foobar($arg, $arg2) {
echo __FUNCTION__, " got $arg and $arg2\n";
}
class foo {
function bar($arg, $arg2) {
echo __METHOD__, " got $arg and $arg2\n";
}
}
// Call the foobar() function with 2 arguments
call_user_func_array("foobar", array("one", "two"));
// Call the $foo->bar() method with 2 arguments
$foo = new foo;
call_user_func_array(array($foo, "bar"), array("three", "four"));//第一个array表示调用$foo实例的bar函数,第二个表示为bar函数的依次参数
如果有命名空间时,调用
namespace Foobar;
class Foo {
static public function test($name) {
print "Hello {$name}!\n";
}
}
// 大于PHP 5.3.0
call_user_func_array(__NAMESPACE__ .'\Foo::test', array('Hannes'));//静态函数简便调用
// PHP 5.3.0 之前
call_user_func_array(array(__NAMESPACE__ .'\Foo', 'test'), array('Philip'));
//传引用
function mega(&$a){//&5.4以前可省略,后不行,还是写完整
$a = 55;
echo "function mega \$a=$a\n";
}
$bar = 77;
call_user_func_array('mega',array(&$bar));
echo "global \$bar=$bar\n";
function mega $a=55 global $bar=55 //引用生效
62、在函数中注册有多个回调内容时(如使用 call_user_func() 与 call_user_func_array()),如在前一个回调中有未捕获的异常,其后的将不再被调用
63、伪类
number 说明一个参数可以是 integer 或者 float
void 作为返回类型意味着函数的返回值是无用的。void 作为参数列表意味着函数不接受任何参数。
在函数原型中,$...
表示等等的意思。当一个函数可以接受任意个参数时使用此变量名。
64、类型转换
允许的强制转换有:
(int), (integer) - 转换为整形 integer
(bool), (boolean) - 转换为布尔类型 boolean
(float), (double), (real) - 转换为浮点型 float
(string) - 转换为字符串 string
(array) - 转换为数组 array
(object) - 转换为对象 object
(unset) - 转换为 NULL (PHP 5)
$binary = (binary)$string;
$binary = b"binary string";//转化为二进制字符串(php5.2 +)
$avar = "中国";
var_dump((binary)$avar);
var_dump(b"$avar");
string(6) "中国" string(6) "中国" //??啥意思 不是二进制??
65、变量语法
$
区分大小写,字母或下划线开头,后面任意数量的字母数字下划线
$this 是一个特殊的变量,不能被赋值
$i站点is = 'mansikka'; // 合法变量名;可以用中文
66、以下代码结构会进入全局命名空间:
functions(函数)
classes (类)
interfaces(接口)
constants (常量,非类常量)
在函数/方法之外定义的变量
function yy(){
define('XX','xxx');
$xx = 'xyz';
}
yy();
var_dump(XX);
var_dump($xx);
string(3) "xxx"
NULL
要写出能经受住时间考验的代码,建议给任何进入全局命名空间的符号都加上一个不常见的 3-4 字母的前缀(或后缀),中间用下划线分开。为了避免与其它用户空间代码出现命名空间冲突,建议先研究一下其它项目中已有的前缀(或后缀)并适当地公布出来。示例如下
MyPx_someFunc()
Foo_Date
$asdf_dbh
约定
函数名在两个词中间使用下划线 例如curl_close
类名则使用camelCase 或 PascalCase
__魔术变量,不要用__开头的符号
Iterators 和 Exceptions ?? 迭代器和异常??
67、变量默认值
未初始化的变量具有其类型的默认值 - 布尔类型的变量默认值是 FALSE
,整形和浮点型变量默认值是零,字符串型变量(例如用于 echo 中)默认值是空字符串以及数组变量的默认值是空数组。
isset() 语言结构可以用来检测一个变量是否已被初始化
// String usage; outputs 'string(3) "abc"'
$unset_str .= 'abc';
var_dump($unset_str);
// Object usage; creates new stdClass object (see http://www.php.net/manual/en/reserved.classes.php)
// Outputs: object(stdClass)#1 (1) { ["foo"]=> string(3) "bar" }
$unset_obj->foo = 'bar';
var_dump($unset_obj);
68、如果register_globals值为false,PHP5.4已剔除这个
为了得到 DOCUMENT_ROOT 的值,将必须使用$_SERVER['DOCUMENT_ROOT'] 代替 $DOCUMENT_ROOT,又如,使用 $_GET['id'] 来代替 $id
69、预定义变量
1、超全局变量
$GLOBALS --引用全局作用域中可用的全部变量
$_SERVER
$_GET
$_POST
$_FILES
$_COOKIE
$_SESSION
$_REQUEST
$_ENV //环境变量
2、其他预定义变量
$_COOKIE — HTTP Cookies
$php_errormsg — 前一个错误信息
$HTTP_RAW_POST_DATA — 原生POST数据
$http_response_header — HTTP 响应头
$argc — 传递给脚本的参数数目
$argv — 传递给脚本的参数数组
70、获取原生POST数据
$HTTP_RAW_POST_DATA 一般而言,使用php://input 代替
php:// — 访问各个输入/输出流
71、函数中不可直接使用全局变量,要访问有两个方法
1、加一个global 的关键字
2、$GLOBALS['b'] 使用超全局变量
注意其他预定义变量 不是超全局 所以还是需要global关键字 如$HTTP_RAW_POST_DATA
72、静态变量
关键字 static
静态变量仅在局部函数域中存在,但当程序执行离开此作用域时,其值并不丢失
function test()
{
static $a = 0;
echo $a;
$a++;
}//使用递归,以前开发都是传参数进去,原来有更方便的static关键字
其实放在全局空间内,并没有报错,但是无意义
注意:static 赋值时不能用表达式
static $a = 1+1; //错误
73、Zend Engine 编译器和执行器
Zend Engine最主要的特性就是把PHP的边解释边执行的运行方式改为先进行预编译(Compile),然后再执行(Execute) 类似GCC
74、
function test_global_ref() {
global $obj;
$obj = &new stdclass;//这个php7.2会报语法错误
}
function test_global_noref() {
global $obj;
$obj = new stdclass;//正确用法
}
test_global_ref();
var_dump($obj);
test_global_noref();
var_dump($obj);
75、引用:用两个变量来指向同一个内容,指向了同一个地方
75.1、引用是什么
在 PHP 中引用意味着用不同的名字访问同一个变量内容,变量名和变量内容是不一样的, 因此同样的内容可以有不同的名字。引用可以被看作是 Unix 文件系统中的硬链接。参见76
75.2、引用做什么
第一件事:PHP 的引用允许用两个变量来指向同一个内容
(1)、如果对一个未定义的变量进行引用赋值、引用参数传递或引用返回,则会自动创建该变量。
<?php
function foo(&$var) { }
foo($a); // $a is "created" and assigned to null
$b = array();
foo($b['b']);
var_dump(array_key_exists('b', $b)); // bool(true)
$c = new StdClass;
foo($c->d);
var_dump(property_exists($c, 'd')); // bool(true)
(2)、同样的语法可以用在函数中,它返回引用,以及用在 new 运算符中(自 PHP 5 起,new 自动返回对象的引用)
$bar =& new fooclass();// php5 之后会报错
$foo =& find_var($bar);
(3)、如果在一个函数内部给一个声明为 global 的变量赋于一个引用,该引用只在函数内部可见。可以通过使用 $GLOBALS 数组避免这一点。
$a = 123;
$b = 456;
function a(){
global $a,$b;
$a = &$b;或$GLOBALS["a"] = &$b;
echo $a;
}
a();//456 或123
echo $a;//123 或456
把 global $var; 当成是 $var =& $GLOBALS['var']; 的简写。从而将其它引用赋给 $var 只改变了本地变量的引用。
第二件事:引用做的第二件事是用引用传递变量
可以将一个变量通过引用传递给函数,这样该函数就可以修改其参数的值
function foo(&$var)//注意在函数调用时没有引用符号——只有函数定义中有,光是函数定义就足够使参数通过引用来正确传递了
{
$var++;
}
$a=5;
foo($a);
三种情况可以通过引用传递
变量,例如 foo($a)
New 语句,例如 foo(new foobar())
从函数中返回的引用,例如:
function &bar()
{
$a = 5;
return $a;
}
foo(bar());//相见引用返回
任何其它表达式都不能通过引用传递
第三件事:引用做的第三件事是引用返回
定义:用在当想用函数找到引用应该被绑定在哪一个变量上面时
不要用返回引用来增加性能,引擎足够聪明来自己进行优化。仅在有合理的技术原因时才返回引用
class foo {
public $value = 42;
public function &getValue() {
return $this->value;
}
}
$obj = new foo;
$myValue = &$obj->getValue(); // $myValue is a reference to $obj->value, which is 42.
$obj->value = 2;
echo $myValue; // prints the new value of $obj->value, i.e. 2.
//和参数传递不同,这里必须在两个地方都用 & 符号——指出返回的是一个引用,而不是通常的一个拷贝,同样也指出 $myValue 是作为引用的绑定,而不是通常的赋值。
75.3、引用不是什么
引用不是指针
function foo(&$var)
{
$var =& $GLOBALS["baz"];
}
foo($bar);
var只能更改baz,不能更改bar;
75.3、取消引用
当 unset 一个引用,只是断开了变量名和变量内容之间的绑定。这并不意味着变量内容被销毁了
75.4、引用定位
许多 PHP 的语法结构是通过引用机制实现的
当用 global $var 声明一个变量时实际上建立了一个到全局变量的引用,等于$var =& $GLOBALS["var"];
在一个对象的方法中,$this 永远是调用它的对象的引用
76、unix文件系统中的硬链接和软连接
硬链接:
一般情况下,文件名和inode号码是"一一对应"关系,每个inode号码对应一个文件名。但是,Unix/Linux系统允许,多个文件名指向同一个inode号码。
这意味着,可以用不同的文件名访问同样的内容;对文件内容进行修改,会影响到所有文件名;但是,删除一个文件名,不影响另一个文件名的访问。这种情况就被称为"硬链接"(hard link)。
共用同一个索引的许多不同名文件,修改一个文件会影响所有其他的文件,但是删除单个文件其他文件依然存在,只有在所有硬链接连接的文件都被删除之后,inode才会被释放。
软连接:
文件A和文件B的inode号码虽然不一样,但是文件A的内容是文件B的路径。读取文件A时,系统会自动将访问者导向文件B。因此,无论打开哪一个文件,最终读取的都是文件B。这时,文件A就称为文件B的"软链接"(soft link)或者"符号链接(symbolic link)。
这意味着,文件A依赖于文件B而存在,如果删除了文件B,打开文件A就会报错:"No such file or directory"。这是软链接与硬链接最大的不同:文件A指向文件B的文件名,而不是文件B的inode号码,文件B的inode"链接数"不会因此发生变化。
77、可变变量
$a = 'Hello';
$$a = 'World';
用于数组$$a[1],摸棱两可
${$a[1]}:$a[1]作为变量
${$a}[1]:$$a作为变量,并取出索引1
类中数组属性:
$fool->$arr[1]:先计算数组值,再取属性
$fool->{$arr}[1]:先取属性,再取数组值
超全局变量和$this不能作为可变变量使用
78、来自php之外的变量
POST/GET html表单访问数据
$_POST
$_REQUEST //默认情况下包含了 $_GET,$_POST 和 $_COOKIE 的数组
$_GET
将 GET/POST/Cookie 变量导入到全局作用域中
import_request_variables('p or g or c', 'ud_'): bool //p代表post,g代表get,c代表cookie,ud_代表给变量加前缀
如果 PHP 指令 register_globals = on
html提交的变量自动导入到全局作用域,用import_request_variables更好
硬链接:
一般情况下,文件名和inode号码是"一一对应"关系,每个inode号码对应一个文件名。但是,Unix/Linux系统允许,多个文件名指向同一个inode号码。
这意味着,可以用不同的文件名访问同样的内容;对文件内容进行修改,会影响到所有文件名;但是,删除一个文件名,不影响另一个文件名的访问。这种情况就被称为"硬链接"(hard link)。
共用同一个索引的许多不同名文件,修改一个文件会影响所有其他的文件,但是删除单个文件其他文件依然存在,只有在所有硬链接连接的文件都被删除之后,inode才会被释放。
软连接:
文件A和文件B的inode号码虽然不一样,但是文件A的内容是文件B的路径。读取文件A时,系统会自动将访问者导向文件B。因此,无论打开哪一个文件,最终读取的都是文件B。这时,文件A就称为文件B的"软链接"(soft link)或者"符号链接(symbolic link)。
这意味着,文件A依赖于文件B而存在,如果删除了文件B,打开文件A就会报错:"No such file or directory"。这是软链接与硬链接最大的不同:文件A指向文件B的文件名,而不是文件B的inode号码,文件B的inode"链接数"不会因此发生变化。
77、可变变量
$a = 'Hello';
$$a = 'World';
用于数组$$a[1],摸棱两可
${$a[1]}:$a[1]作为变量
${$a}[1]:$$a作为变量,并取出索引1
类中数组属性:
$fool->$arr[1]:先计算数组值,再取属性
$fool->{$arr}[1]:先取属性,再取数组值
超全局变量和$this不能作为可变变量使用
78、来自php之外的变量
POST/GET html表单访问数据
$_POST
$_REQUEST //默认情况下包含了 $_GET,$_POST 和 $_COOKIE 的数组
$_GET
将 GET/POST/Cookie 变量导入到全局作用域中
import_request_variables('p or g or c', 'ud_'): bool //p代表post,g代表get,c代表cookie,ud_代表给变量加前缀
如果 PHP 指令 register_globals = on
html提交的变量自动导入到全局作用域,用import_request_variables更好