PHP教程之PHP 5/Zend Engine 2.0的改善
没有人会喜欢和见异思迁的人交朋友,因为这种人太不安分,太不可靠,因此,你必须要强迫自己完成自己的目标,哪怕可能会很难受,也得坚持,毅力就是这么锻炼出来的。 近两年没有利用PHP写进程序了,明天要用PHP,就在网上查了查,看到了PHP5,一时之间乐趣又大了起来,因而翻译了这篇文章。文章来历于http://www.php.net/。
新的对象模子
PHP中的对象处置局部已完整重写,具有更佳的功能和更多的功效。在先前的PHP版本中,对象被当作原始的复杂类型
(如integer和string)来处置,这类办法的弱点是当变量被赋值或作为参数传递时,失掉的是对象拷贝。而在新版本中,
对象是经由过程句柄来援用的,而不是经由过程对象的值(句柄想象为对象的标识符)。
良多PHP法式员能够未意想到老的对象模子的“copying quirks“,因而之前的大多半PHP法式将不需求做任何更改
便可运转,或只做很少的修改。
公有和回护成员
PHP 5引进了公有和回护成员变量,它们可以界说可视化的类属性。
示例
回护成员变量能在该类的子类中被会见,而公有成员变量只能在所属类中被会见。
<?phpclass MyClass { private $Hello = "Hello, World!\n"; protected $Bar = "Hello, Foo!\n"; protected $Foo = "Hello, Bar!\n"; function printHello() { print "MyClass::printHello() " . $this->Hello; print "MyClass::printHello() " . $this->Bar; print "MyClass::printHello() " . $this->Foo; }}class MyClass2 extends MyClass { protected $Foo; function printHello() { MyClass::printHello(); /* Should print */ print "MyClass2::printHello() " . $this->Hello; /* Shouldn't print out anything */ print "MyClass2::printHello() " . $this->Bar; /* Shouldn't print (not declared)*/ print "MyClass2::printHello() " . $this->Foo; /* Should print */ }}$obj = new MyClass();print $obj->Hello; /* 不输入任何内容,以下类同 */print $obj->Bar; /* Shouldn't print out anything */print $obj->Foo; /* Shouldn't print out anything */$obj->printHello(); /* Should print */$obj = new MyClass2();print $obj->Hello; /* Shouldn't print out anything */print $obj->Bar; /* Shouldn't print out anything */print $obj->Foo; /* Shouldn't print out anything */$obj->printHello();?>
公有和回护办法
PHP 5(ZEND引擎2)中,公有办法和回护办法也被引入。
示例:
<?phpclass Foo { private function aPrivateMethod() { echo "Foo::aPrivateMethod() called.\n"; } protected function aProtectedMethod() { echo "Foo::aProtectedMethod() called.\n"; $this->aPrivateMethod(); }}class Bar extends Foo { public function aPublicMethod() { echo "Bar::aPublicMethod() called.\n"; $this->aProtectedMethod(); }}$o = new Bar;$o->aPublicMethod();?>
之前代码中的用户自界说类或办法中固然没有界说"public," "protected" 或 "private"等关头字,但无需修正便可运转。
笼统类和办法
PHP 5还引入了笼统类和办法。笼统办法只声明办法的”符号”,而不供应它的完成。一个包括笼统办法的类需求声明为”abstract”。
例如:
<?phpabstract class AbstractClass { abstract public function test();}class ImplementedClass extends AbstractClass { public function test() { echo "ImplementedClass::test() called.\n"; }}$o = new ImplementedClass;$o->test();?>
笼统类不克不及实例化。
旧的代码中的用户自界说类或办法中虽不决义"abstract”关头字,但无需修正就能够运转。
接口(Interfaces)
ZEND引擎2.0引入了接口。一个类可以完成恣意的接口列表。
例如:
<?phpinterface Throwable { public function getMessage();}class Exception implements Throwable { public function getMessage() { // ...}?>
旧的代码中的用户界说类或办法中固然没有界说"interface”关头字,但无需修正就能够正常运转。
类类型提醒(Class Type Hints)
在保存类无需界说类型的同时,PHP 5引入了类类型提醒来声明,以希冀把对象的类经由过程参数传递给一个办法。
例如:
<?phpinterface Foo { function a(Foo $foo);}interface Bar { function b(Bar $bar);}class FooBar implements Foo, Bar { function a(Foo $foo) { // ... } function b(Bar $bar) { // ... }}$a = new FooBar;$b = new FooBar;$a->a($b);$a->b($b);?>
这些类类型提醒不是象一些需求类型界说的言语那样在编译中停止反省,而是在运转时停止反省。这就意味着:
<?phpfunction foo(ClassName $object) { // ...}?>
is equivalent to:
<?phpfunction foo($object) { if (!($object instanceof ClassName)) { die("Argument 1 must be an instance of ClassName"); }}?>
这类语法只用于对象或类,不合用于内建(built-in)类型。
Final关头字(final)
PHP 5引入了“final”关头字以界说在子类中不克不及被掩盖的成员或办法。
例:
<?php
class Foo { final function bar() { // ... }}?>
之前所写代码中的用户自界说类或办法中虽不决义"final"关头字,但无需修正就能够运转了。
对象克隆(Object Cloning)
PHP 4在对象被复制时,用户不克不及判别运转谁人拷贝机关函数。在复制时,PHP 4依据对象的属性
一名一名地复制一个一样的复成品。
每次都要创立一个完整一样的复成品其实不老是咱们想要的。一个很好的复制机关例子是,当有
一个代表一个GTK窗口的对象,它具有该窗口的一切资本,当你创立一个拷贝时,你能够需求一
个新的窗口,它具有原窗口的一切属性,但需求具有新窗口的资本。别的一个例子是你有一个
对象援用了别的一个对象,当你复制父对象时,你但愿创立谁人援用对象的新实例,以使复成品有一个独自的拷贝。
对一个对象的拷贝经由过程挪用对象的__clone()办法完成:
<?php
$copy_of_object = $object->__clone();
?>
当开辟者恳求创立一个对象的新的拷贝时,ZEND引擎会反省是不是已界说了__clone()办法。假如不决义
的话,它会挪用一个默许的__clone()办法来复制该对象的一切属性。假如界说了该办法,该办法会担任
在拷贝中设置需要的属性。为利用便利,引擎会供应一个函数从源对象中导入一切的属性,如许它便可
以先失掉一个具有值的源对象拷贝,然后只需求对需求改动的属性停止掩盖便可。
例:
<?php
class MyCloneable {
static $id = 0;
function MyCloneable() {
$this->id = self::$id++;
}
function __clone() {
$this->name = $that->name;
$this->address = "New York";
$this->id = self::$id++;
}
}
$obj = new MyCloneable();
$obj->name = "Hello";
$obj->address = "Tel-Aviv";
print $obj->id . "\n";
$obj = $obj->__clone();
print $obj->id . "\n";
print $obj->name . "\n";
print $obj->address . "\n";
?>
一致的机关办法
ZEND引擎答应开辟者界说类的机关办法。具有机关办法的类在新建时会起首挪用机关办法,机关
办法合用于在正式利用该类行进行的初始化。
在PHP4中,机关办法的称号与类名不异。因为在派生类中挪用父类的作法对照广泛,因而招致在
PHP4中当类在一个大型的类承继中停止挪动时,处置体例有点愚笨。当一个派生类被挪动到一个分歧
的父类中时,父类的机关办法名必定是分歧的,如许的话派生类中的有关挪用父类机关办法的语句需求改写。
PHP5引入了一个界说机关办法的尺度体例,经由过程挪用它们的__construct()来界说。
示例:
<?php
class BaseClass {
function __construct() {
print "In BaseClass constructor\n";
}
}
class SubClass extends BaseClass {
function __construct() {
parent::__construct();
print "In SubClass constructor\n";
}
}
$obj = new BaseClass();
$obj = new SubClass();
?>
为向后兼容,当PHP5类不克不及找到__construct()办法时,会经由过程老的办法也就是类名
来查找机关办法。这意味着独一能够发生兼容性成绩的是在之前的代码中已利用了
一个名为__construct()的办法名。
析构办法
界说析构办法是非常有效的。析构办法可以纪录调试信息,封闭数据库毗连,还有做其它的收尾
任务。PHP4中并没有此机制,虽然PHP已撑持注册在恳求停止时需求运转的函数。
PHP5引入了与其它面向对象言语如Java言语类似的析构办法:当最初一个该对象的援用被排除时,
体系将会在该对象从内存中释放前挪用名为__destruct()的析构办法。
示例:
<?php
class MyDestructableClass {
function __construct() {
print "In constructor\n";
$this->name = "MyDestructableClass";
}
function __destruct() {
print "Destroying " . $this->name . "\n";
}
}
$obj = new MyDestructableClass();
?>
和机关办法类似,引擎将不挪用父类的析构办法,为挪用该办法,你需求在子
类的析构办法中经由过程parent::__destruct()语句停止挪用。
常量
PHP 5 引入了类常量(per-class constants)界说:
<?php
class Foo {
const constant = "constant";
}
echo "Foo::constant = " . Foo::constant . "\n";
?>
PHP5答应常量中包括表达式,但在编译经常量中的表达式将被盘算,
因而常量不克不及在运转中改动它的值。
<?php
class Bar {
const a = 1<<0;
const b = 1<<1;
const c = a | b;
}
?>
之前代码中的用户自界说类或办法中固然不决义"const”关头字,
但无需修正就能够运转。
异常(Exceptions)
PHP4中没异常处置,PHP5引入了与其它与言语类似的异常处置模子。
<?php
class MyExceptionFoo extends Exception {
function __construct($exception) {
parent::__construct($exception);
}
}
try {
throw new MyExceptionFoo("Hello");
} catch (MyExceptionFoo $exception) {
print $exception->getMessage();
}
?>
之前代码中的用户自界说类或办法中虽不决义'catch', 'throw' 和 'try'关头字,但无需修正
就能够运转。
函数前往对象值
在PHP4中,函数不成能前往对象的值并对前往的对象停止办法挪用,跟着Zend Engine 2
(ZEND引擎2)的呈现,以下挪用成为能够:
<?php
class Circle {
function draw() {
print "Circle\n";
}
}
class Square {
function draw() {
print "Square\n";
}
}
function ShapeFactoryMethod($shape) {
switch ($shape) {
case "Circle":
return new Circle();
case "Square":
return new Square();
}
}
ShapeFactoryMethod("Circle")->draw();
ShapeFactoryMethod("Square")->draw();
?>
静态类中的静态成员变量可初始化
例如:
<?php
class foo {
static $my_static = 5;
}
print foo::$my_static;
?>
静态办法(Static Methods)
PHP5引入了关头字'static'来界说一个静态办法,如许可以从对象外停止挪用。
例如:
<?php
class Foo {
public static function aStaticMethod() {
// ...
}
}
Foo::aStaticMethod();
?>
虚拟变量$this在被界说为静态(static)的办法中有效。
Instanceof
PHP5引入了 “instanceof“关头字来肯定一个对象是不是是某一个对象的实例,或某一个对象的派生,或利用了某一个接口。
示例:
<?php
class baseClass { }
$a = new baseClass;
if ($a instanceof basicClass) {
echo "Hello World";
}
?>
静态函数变量(Static function variables)
一切的静态变量如今在编译时停止处置,这答应开辟者经由过程援用来指定静态变量。这个变更进步了效力但意味着不成能对静态变量停止直接援用。
函数中经由过程援用体例传递的参数答应有默许值
例如:
<?php
function my_function(&$var = null) {
if ($var === null) {
die("$var needs to have a value");
}
}
?>
__autoload()
在初始化一个不决义的类时,__autoload()拦阻函数(interceptor function)将被主动调
用。类名将作为__autoload()拦阻函数独一参数传递给它。
例如:
<?php
function __autoload($className) {
include_once $className . ".php";
}
$object = new ClassName;
?>
办法和属性挪用的重载
一切办法挪用和属性会见都可以通用 __call(), __get() 和 __set()办法来重载。
例: __get() 和 __set()
<?php
class Setter {
public $n;
public $x = array("a" => 1, "b" => 2, "c" => 3);
function __get($nm) {
print "Getting [$nm]\n";
if (isset($this->x[$nm])) {
$r = $this->x[$nm];
print "Returning: $r\n";
return $r;
} else {
print "Nothing!\n";
}
}
function __set($nm, $val) {
print "Setting [$nm] to $val\n";
if (isset($this->x[$nm])) {
$this->x[$nm] = $val;
print "OK!\n";
} else {
print "Not OK!\n";
}
}
}
$foo = new Setter();
$foo->n = 1;
$foo->a = 100;
$foo->a++;
$foo->z++;
var_dump($foo);
?>
示例: __call()
<?php
class Caller {
var $x = array(1, 2, 3);
function __call($m, $a) {
print "Method $m called:\n";
var_dump($a);
return $this->x;
}
}
$foo = new Caller();
$a = $foo->test(1, "2", 3.4, true);
var_dump($a);
?>
总的来说,在这一个月左右的时间中,学到的不少,但是也遇到不少的问题,比如批量图片的上传,一直到现在也不懂,如何实现动态的增加上传图片的数量。 微软最近出的新字体“微软雅黑”,虽然是挺漂亮的,不过firefox支持的不是很好,所以能少用还是少用的好。 最后介绍一个代码出错,但是老找不到错误方法,就是 go to wc (囧),出去换换气没准回来就找到错误啦。 你很难利用原理去编写自己的代码。对于php来说,系统的学习我认为还是很重要的,当你有一定理解后,你可你针对某种效果研究,我想那时你不会只是复制代码的水平了。 作为一个合格的coder 编码的规范是必须,命名方面我推崇“驼峰法”,另外就是自己写的代码最好要带注释,不然时间长了,就算是自己的代码估计看起来都费事,更不用说别人拉。 首先我是坚决反对新手上来就用框架的,因为对底层的东西一点都不了解,造成知识上的真空,会对以后的发展不利。我的观点上手了解下框架就好,代码还是手写。当然啦如果是位别的编程语言的高手的话,这个就另当别论啦。 php是动态网站开发的优秀语言,在学习的时候万万不能冒进。在系统的学习前,我认为不应该只是追求实现某种效果,因为即使你复制他人的代码调试成功,实现了你所期望的效果,你也不了解其中的原理。 有时候汉字的空格也能导致页面出错,所以在写代码的时候,要输入空格最好用引文模式。 做为1门年轻的语言,php一直很努力。 你很难利用原理去编写自己的代码。对于php来说,系统的学习我认为还是很重要的,当你有一定理解后,你可你针对某种效果研究,我想那时你不会只是复制代码的水平了。 至于模板嘛,各位高人一直以来就是争论不休,我一只小菜鸟就不加入战团啦,咱们新手还是多学点东西的好。 先学习php和mysql,还有css(html语言很简单)我认为现在的效果比以前的方法好。 找到的的资料很多都是在论坛里的,需要注册,所以我一般没到一个论坛都注册一个id,所有的id都注册成一样的,这样下次再进来的时候就不用重复注册啦。当然有些论坛的某些资料是需要的付费的。 你很难利用原理去编写自己的代码。对于php来说,系统的学习我认为还是很重要的,当你有一定理解后,你可你针对某种效果研究,我想那时你不会只是复制代码的水平了。 首推的搜索引擎当然是Google大神,其次我比较喜欢 百度知道。不过搜出来的结果往往都是 大家copy来copy去的,运气的的概率很大。 最后祝愿,php会给你带来快乐的同时 你也会给他带来快乐。 首先我是坚决反对新手上来就用框架的,因为对底层的东西一点都不了解,造成知识上的真空,会对以后的发展不利。我的观点上手了解下框架就好,代码还是手写。当然啦如果是位别的编程语言的高手的话,这个就另当别论啦。 其实没啥难的,多练习,练习写程序,真正的实践比看100遍都有用。不过要熟悉引擎 你很难利用原理去编写自己的代码。对于php来说,系统的学习我认为还是很重要的,当你有一定理解后,你可你针对某种效果研究,我想那时你不会只是复制代码的水平了。 曾经犯过一个很低级的错误,我在文件命名的时候用了一个横线\\\\\\\'-\\\\\\\' 号,结果找了好几个小时的错误,事实是命名的时候 是不能用横线 \\\\\\\'-\\\\\\\' 的,应该用的是下划线\\\\\\\'_\\\\\\\' ;
页:
[1]