如果我有课,
abstract class Parent {
abstract function foo();
}
class Child extends Parent {
function foo($param) {
//stuff
}
}
我收到一个错误,因为抽象声明没有任何参数,但是孩子的实现却没有。我正在使用抽象函数创建一个适配器父类,这些抽象函数在实现时可能具有可变数量的参数,具体取决于子类的上下文。有没有结构化的方法可以解决这个问题,还是我必须使用func_get_args?
答案 0 :(得分:12)
PHP这样做是为了保护多态性。继承类型的任何对象都应该可以使用,就像它们是父类型一样。
考虑以下课程:
abstract class Animal {
abstract function run();
}
class Chicken extends Animal {
function run() {
// Clever code that makes a chicken run
}
}
class Horse extends Animal {
function run($speed) {
// Clever code that makes a horse run at a specific speed
}
}
...以及以下代码:
function makeAnimalRun($animal) {
$animal->run();
}
$someChicken = new Chicken();
$someHorse = new Horse();
makeAnimalRun($someChicken); // Works fine
makeAnimalRun($someHorse); // Will fail because Horse->run() requires a $speed
makeAnimalRun
应该能够在run
的继承类的任何实例上执行Animal
,但自Horse
run
的实现以来{ {1}}需要$speed
参数,$animal->run()
中的makeAnimalRun
来电失败。
幸运的是,这很容易解决。您只需要在重写方法中为参数提供默认值。
class Horse extends Animal {
function run($speed = 5) {
// Clever code that makes that horse run at a specific speed
}
}
答案 1 :(得分:3)
如果要在函数中使用变量参数,则必须使用func_get_args。请注意,func_get_args获取传递给PHP函数的所有参数。
但是,您可以通过在函数中包含相应的参数来强制传递最少数量的参数。
例如: 假设你有一个你希望用至少一个参数调用的函数。然后写下以下内容:
function foo($param) {
//stuff
$arg_list = func_get_args();
}
现在您已经定义了foo(),您必须至少使用一个参数调用它。你也可以选择传递可变数量的参数n,其中n> 1,并通过func_get_args()接收这些参数。请记住,上面的$ arg_list还将包含$ param的副本作为其第一个元素。