我有一个类似这样的PHP类:

class ParentClass {

function __construct($arg) {

// Initialize a/some variable(s) based on $arg

}

}

它有一个子类,例如:

class ChildClass extends ParentClass {

function __construct($arg) {

// Let the parent handle construction.

parent::__construct($arg);

}

}

如果出于某种原因,ParentClass需要更改为接受多个可选参数,我希望我的子类提供"以防万一"参数,该怎么办?除非我重新编写childclass代码,否则它将只把一个参数带到构造函数,并且只传递一个参数。

这是如此罕见还是如此糟糕,以至于通常情况下,子类不需要从采用不同参数的ParentClass继承?

基本上,我在python中看到过,在这里可以通过somefunction(*args)将可能未知数量的参数传递给函数,其中"args"是某种类型的数组/iterable。PHP中是否存在类似的内容?或者我应该在继续之前重构这些类吗?

这可以在php>5.6中通过使用EDOCX1(splat)操作符在不使用call_user_func_array()的情况下完成:

public function __construct()

{

parent::__construct(...func_get_args());

}

在PHP中有类似的内容,尽管有点冗长:

$args = func_get_args();

call_user_func_array(array($this, 'parent::__construct'), $args);

这会导致php 5.4.14上出现无限循环

如果$this指向不同的类,将不起作用。

在5.5(可能更早)中,您可以这样做:call_user_func_array('parent::__construct', func_get_args());;

@ogc nick我刚刚在5.2到5.6版本上成功地尝试过。

请参阅我的答案,了解如何在php 5.6及更高版本中不使用call_user_func_array()。

如果出现PHP嵌套限制错误,请尝试以下操作:

$args = func_get_args();

call_user_func_array(array('parent', '__construct'), $args);

来源:nl3.php.net/manual/en/function.call user func array.php 9499‌&8203;3

这是有效的,不会引入无限循环。

我的方法(在php 7.1中测试):

class ParentClass {

public function __construct(...$args) {

print 'Parent: ' . count($args) . PHP_EOL;

}

}

class ChildClass extends ParentClass {

public function __construct(...$args) {

parent::__construct(...$args);

print 'Child: ' . count($args). PHP_EOL;

}

}

$child = new ChildClass(1, 2, 3, new stdClass);

//Output:

//Parent: 4

//Child: 4

测试https://3v4l.org/csj68

在这种情况下,父级和子级具有相同的构造函数签名。如果要在父构造函数中解包参数,它也可以工作:

class ParentClass {

public function __construct($a, $b, $c, $d = null) {

print 'Parent: ' . $a .  $b .  $c . PHP_EOL;

}

}

class ChildClass extends ParentClass {

public function __construct(...$args) {

parent::__construct(...$args);

}

}

$child = new ChildClass(1, 2, 3);

//Output: Parent: 123

测试https://3v4l.org/jge1a

值得注意的是,在php>=5.6中,可以强制变量函数的类型(php>=7中的标量类型):

class ParentClass {

public function __construct(DateTime ...$args) {

//Do something

}

}

在php.net上查看这些函数:

此外,如果要进行可选参数,可以执行以下操作:

class ParentClass {

function __construct($arg, $arg2="Default Value") {

// Initialize a/some variable(s) based on $arg

}

}

是的,制作一个使用与父类不同的构造函数参数的子类是非常糟糕的做法。尤其是在像PHP这样的语言中,它的支持很差。

当然,在PHP中传递一组"我们可能想要的任何参数"的通用方法是传递一个由配置值数组组成的单个参数。

当然,你有"神奇容器"的代码味道(c2.com/cgi/wiki?魔术师容器)。您需要的是一个参数对象(c2.com/cgi/wiki)?参数对象)。

然而,不幸的是,magic容器在PHP应用程序中被广泛使用。

OP询问父类添加新构造函数参数的情况。这与更改子类中的参数无关。如果在子构造函数中有额外的初始化逻辑,因此必须调用父构造函数(这可能会更改其参数列表),则此问题的解决方案将非常有用。

parent::__construct( func_get_args() );

hm,不保持参数的顺序(只将它们在第一个参数中放入一个数组)。

php __construct 继承,关于继承:PHP:如何将子类__construct()参数传递给parent :: __ construct()?...相关推荐

  1. php parent construct,PHP:如何传递子类__construct()参数为parent :: __ construct()?

    我有一个像PHP这样的PHP类: class ParentClass { function __construct($arg) { // Initialize a/some variable(s) b ...

  2. php 魔术方法 多继承,day23:单继承多继承菱形继承__init__魔术方法

    原文:https://www.cnblogs.com/libolun/p/13434675.html 单继承 关于继承的一些基本概念 1.什么是子类?什么是父类?如果一个类继承另外一个类,该类叫做子类 ...

  3. java 父类是抽象类 定义private的属性 子类继承_java继承、多态、接口、抽象类定义及应用...

    继承:关键字extends java 中继承是单继承 允许多个子类继承一个父类,不允许一个子类继承多个父类. 继承是继承父类的所有属性和方法,但并不是所有的属性和方法都可被子类调用: 子类继承父类是必 ...

  4. Python---已知Person类,继承Person类生成Teacher类(增加参数:科目)和Student类(增加参数:专业)。

    题目:已知Person类,继承Person类生成Teacher类(增加参数:科目)和Student类(增加参数:专业). 已知Person类如下: class Person(object):# Per ...

  5. 菱形继承,多继承,虚继承、虚表的内存结构全面剖析(逆向分析基础)

    // 声明:以下代码均在Win32_Sp3   VC6.0_DEBUG版中调试通过.. 在逆向还原代码的时候,必须得掌握了菱形继承,多继承,虚继承虚函数的内存虚表结构.所以,这篇文章献给正在学习C++ ...

  6. java多态和继承_Java 继承与多态的深入理解

    Java 继承与多态的深入理解 1.  什么是继承,继承的特点? 子类继承父类的特征和行为,使得子类具有父类的各种属性和方法.或子类从父类继承方法,使得子类具有父类相同的行为. 特点:在继承关系中,父 ...

  7. python面向编程:类继承、继承案例、单继承下属性查找、super方法

    一.类的继承 二.基于继承解决类与类的代码冗余问题 三.在单继承背景下属性的查找 四.super的方法 一.类的继承 1.什么是继承? 在程序中继承是一种新建子类的方法的方式,新创建的类成为子类\派生 ...

  8. 借用构造函数 组合继承 拷贝继承 总结继承

    借用构造函数 <!DOCTYPE html> <html lang="en"> <head><meta charset="UTF ...

  9. C++虚继承(八) --- 虚继承与继承的差异

    前面一篇文章,说明了在C++ 虚继承对基类构造函数调用顺序的影响.经过仔细推敲,发现没有彻底说清楚虚继承与普通继承之间的关系.所以用下面的文字再说明一下. 首先,重复一下虚拟继承与普通继承的区别有: ...

最新文章

  1. System.Transactions深入了解
  2. OAF_开发系列11_实现OAF通过DataBoundValues动态显示表列的左右对齐
  3. 隐藏oracle数据库,如何隐藏Oracle密码
  4. FCN训练自己的数据集及测试
  5. 关于计算机的使用方法中心,关于新校区行政楼和活动中心楼网络使用的说明
  6. P2153-晨跑【费用流,网络流,拆点】
  7. 线程同步 线程安全_同步装饰器来替换线程安全类
  8. socket和http区别有哪些
  9. 在RHEL5/CentOS5上配置使用Open×××
  10. 前端开发 常用选择符与权重0229
  11. (后端)Java中关于金额大小写的工具类
  12. ios上传图片 java_iOS ASIFormDataRequest上传图片 前后台代码
  13. 推荐一份 Google 面试指南
  14. 计算机考试一级b软件未来教育,2019.9全国计算机一级MS Office考试每日一练
  15. 2016考试计算机知识基础题库,2016考试计算机基础知识题库.pdf
  16. P1563 [NOIP2016 提高组] 玩具谜题
  17. 风控建模十一:利用外部数据联合建模时,如何选择样本
  18. Web前端和Web后端的区分
  19. reboot无法进入grub开机选单
  20. 2023养老展|山东养老用品展|老年护理产品展|医养健康展

热门文章

  1. 乐优购物学习笔记(15)
  2. STM32 使用Keil下载仿真时,报错 JLink Info: STM32Fxxxx: Cannot attach to CPU. Trying connect under reset.
  3. IDEA常用快捷键及设置方法
  4. Android滑动展示图片(一页多图,带小圆点,类似小米市场APP详情页图片展示)
  5. 常用xss代码以及绕过
  6. 大学生程序设计邀请赛(华东师范大学)
  7. css 中动态获取宽度,css中的calc动态计算长度值
  8. C++设计原则——迪米特法则
  9. httpie实用指南
  10. ubuntu的快捷键