浅谈PHP中的面向对象OOP中的魔术方法


Posted in PHP onJune 12, 2017

一、什么是魔术方法:

PHP为我们提供了一系列用__开头的函数,这些函数无需自己手动调用,会在合适的时机自动调用,这类函数称为魔术函数。
例如:

function __construct(){} 在new一个新对象时自动调用此函数

二、PHP中都有那些魔术方法,以及它们的作用:

1.__construct():构造函数,new对象时自动调用

eg:

class Person{
    public $name;
    public $age;
    
    function __construct($name,$age){
      $this->name=$name;
      $this->age=$age;
    }
}

 在new新的Person对象时会自动调用__construct()函数,将传入的参数分别赋给$name,$age。

2.__destruct():析构函数,当一个对象被销毁前自动调用

class Person{
    public $name;
    public $age;
    
    function __destruct(){
    echo "这个对象被销毁了";
  }
}

同上所述,对象被销毁时执行此魔术方法

3.__get():访问类中私有属性时自动调用,传递读取属性名,返回$this->属性名

class Person{
    private $name;
    public $age;
    
    function __get($name){
     return $this->$name;
    }
}

如上代码,$name被设为私有属性后不能直接通过$this->name;的方式读取,因此需要设置__get()魔术方法来读取。

4.__set():给类的私有属性赋值时自动调用,传递需设置的属性名,属性值

class Person{
    private $name;
    public $age;
    
    function __set($key,$value){
      $this->$key=$value;
    }
}

同__get()方法,私有属性不能通过$this->name="aaa";的方式直接设置,需要设置__set()方法,传入的参数分别是属性名和属性值。

5.__isset():使用isset检测对象私有属性时调用,传递检测的属性名,返回isset($this->属性名)

class Person{
    private $name;
    public $age;
    
    function __isset($name){
    return isset($this->$name);
  }
}

使用isset检测对象私有属性时调用,其他同上。

6.__unset():使用unset()函数删除对象私有属性时调用,传递删除的属性名,方法中执行unset($this->属性名)

class Person{
    private $name;
    public $age;
    
    function __unset($name){
      unset($this->$name);
    }
}

同上,在用unset()函数删除私有属性时调用。

7.__toString():使用echo打印对象时调用,返回打印对象时想要显示的内容,返回必须是字符串

class Person{
    public $name;
    public $age;
    
    function __toString(){
      $str = <<<str
      您要打印的内容是:<br>
      \$name=>{$this->name};<br>
      \$age=>{$this->age};<br>
str;
      return $str;
    }
}

使用echo打印对象时调用,返回打印对象时想要显示的内容。

8.__call():调用一个类中未定义的或未公开的方法时自动调用,传递被调用的函数名及参数列表

class Person{
    public $name;
    public $age;
    
    function __call($funcName,$funcParams){
      echo "您调用的函数{$funcName},参数列表";
      print_r($funcParams);
      echo "不存在/未公开";
    }
}
$zhangsan=new Person();
$zhangsan->say(1,2,3);

如代码所示,调用不存在的say(1,2,3);时,会打印

您调用的函数way,参数列表Array ( [0] => 123 ) 不存在

9.__clone():当使用clone关键字,克隆一个对象时自动调用,作用是为新克隆的对象初始化赋值

class Person{
    public $name;
    public $age;
    
    function __clone(){
    $this->name="lisi";
    }
}  
$zhangsan=new Person("zhangsan",24);
$lisi=clone $zhangsan;
echo $lisi->name;

打印出的结果是"lisi",而不是"zhangsan"。

10.__sleep():对象序列化时自动调用,返回一个数组,数组中的值就是可以序列化的属性

class Person{
    public $name;
    public $age;
    
   function __sleep(){
    return array("name","age");
  }
}

如上述代码,在用serialize()序列化对象时只有"name","age"属性会被序列化。

11.__wakeup():对象反序列化时自动调用,为反序列化新产生的对象进行初始化赋值

class Person{
    public $name;
    public $age;
    
   function __wakeup(){
    $this -> name = "lisi";
  }
}

将对象序列化后再反序列化,同时给对象的name属性赋初值为"lisi"。

12.__autolode():需要在类外部声明函数,当实例化一个未声明的类时自动调用,传递实例化的类名,可以使用类名自动加载对应的类文件。

function __autoload($className){
  include "class/".strtolower($className).".class.php";
}
  
$zhangsan=new Person();
$zhangsan->say();

如上述代码,Person类不存在时调用__autolode()方法,载入写在文件外的类,"class/".strtolower($className).".class.php";就是类文件的相对路径,$className就是

不在本文件中的类的类名,因此在创建外部类文件时命名方式必须是小写的类名.class.php。__autolode()方法也是惟一一个不用写在类中的魔术方法。

以上就是PHP中的魔术方法,合理利用这些方法可以轻松实现对象的各种操作。希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

PHP 相关文章推荐
php调用mysql存储过程
Feb 14 PHP
php实现zip压缩文件解压缩代码分享(简单易懂)
May 10 PHP
PHP+jQuery+Ajax实现用户登录与退出
Apr 27 PHP
php实现仿写CodeIgniter的购物车类
Jul 29 PHP
PHP发送短信代码分享
Aug 11 PHP
以实例全面讲解PHP中多进程编程的相关函数的使用
Aug 18 PHP
变量在 PHP7 内部的实现(二)
Dec 21 PHP
PHP后台微信支付和支付宝支付开发
Apr 28 PHP
php 删除指定文件夹的实例讲解
Jul 25 PHP
PHP开启目录引索+fancyindex漂亮目录浏览带搜索功能
Sep 23 PHP
laravel 获取某个查询的查询SQL语句方法
Oct 12 PHP
laravel5.5安装jwt-auth 生成token令牌的示例
Oct 24 PHP
用php+ajax新建流程(请假、进货、出货等)
Jun 11 #PHP
详解PHP函数 strip_tags 处理字符串缺陷bug
Jun 11 #PHP
php模仿qq空间或朋友圈发布动态、评论动态、回复评论、删除动态或评论的功能(中)
Jun 11 #PHP
PHP中error_reporting函数用法详细介绍
Jun 11 #PHP
详解PHP处理字符串类似indexof的方法函数
Jun 11 #PHP
PHP获取文件扩展名的方法实例总结
Jun 10 #PHP
PHP获取数组中单列值的方法
Jun 10 #PHP
You might like
php IP及IP段进行访问限制的代码
2008/12/17 PHP
深入file_get_contents与curl函数的详解
2013/06/25 PHP
PHP 类与构造函数解析
2017/02/06 PHP
Laravel框架中集成MongoDB和使用详解
2019/10/17 PHP
Javascript实现的分页函数
2007/02/07 Javascript
js原生appendChild的bug解决心得分享
2013/07/01 Javascript
深入解析JavaScript中的变量作用域
2013/12/06 Javascript
jquery设置按钮停顿3秒不可用
2014/03/07 Javascript
Javascript判断图片尺寸大小实例分析
2014/06/16 Javascript
jquery操作对象数组元素方法详解
2014/11/26 Javascript
JS中字符串trim()使用示例
2015/05/26 Javascript
JQuery 设置checkbox值二次无效的解决方法
2016/07/22 Javascript
Bootstrap中表单控件状态(验证状态)
2016/08/04 Javascript
angular.JS实现网页禁用调试、复制和剪切
2017/03/31 Javascript
Jquery中attr与prop的区别详解
2017/05/27 jQuery
vue.js移动端app之上拉加载以及下拉刷新实战
2017/09/11 Javascript
jquery 一键复制到剪切板的实例
2017/09/20 jQuery
vue 添加vux的代码讲解
2017/11/30 Javascript
AngularJS $http post 传递参数数据的方法
2018/10/09 Javascript
Node快速切换版本、版本回退(降级)、版本更新(升级)
2021/01/07 Javascript
JavaScript实现点击出现子菜单效果
2021/02/08 Javascript
[01:20]2018DOTA2亚洲邀请赛总决赛战队LGD晋级之路
2018/04/07 DOTA
Python实现从URL地址提取文件名的方法
2015/05/15 Python
实例讲解Python的函数闭包使用中应注意的问题
2016/06/20 Python
Python使用email模块对邮件进行编码和解码的实例教程
2016/07/01 Python
Python爬虫包 BeautifulSoup  递归抓取实例详解
2017/01/28 Python
HTML中使用python屏蔽一些基本功能的方法
2017/07/07 Python
Python编程实现控制cmd命令行显示颜色的方法示例
2017/08/14 Python
使用python和pygame绘制繁花曲线的方法
2018/02/24 Python
Python 列表推导式需要注意的地方
2020/10/23 Python
详解android与HTML混合开发总结
2018/06/06 HTML / CSS
Expedia马来西亚旅游网站:廉价酒店,度假村和航班预订
2016/07/26 全球购物
OPPO手机官方商城:中国手机市场出货量第一品牌
2017/10/18 全球购物
Window server中安装Redis的超详细教程
2021/11/17 Redis
MySQL创建管理子分区
2022/04/13 MySQL
Python如何快速找到多个字典中的公共键(key)
2022/04/29 Python