php 在函数中使用默认参数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/9166914/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Using Default Arguments in a Function
提问by renosis
I am confused about default values for PHP functions. Say I have a function like this:
我对 PHP 函数的默认值感到困惑。说我有一个这样的功能:
function foo($blah, $x = "some value", $y = "some other value") {
// code here!
}
What if I want to use the default argument for $x and set a different argument for $y?
如果我想对 $x 使用默认参数并为 $y 设置不同的参数怎么办?
I have been experimenting with different ways and I am just getting more confused. For example, I tried these two:
我一直在尝试不同的方法,但我越来越困惑。例如,我尝试了这两个:
foo("blah", null, "test");
foo("blah", "", "test");
But both of those do not result in a proper default argument for $x. I have also tried to set it by variable name.
但是这两者都不会导致 $x 的正确默认参数。我也尝试通过变量名设置它。
foo("blah", $x, $y = "test");
I fully expected something like this to work. But it doesn't work as I expected at all. It seems like no matter what I do, I am going to have to end up typing in the default arguments anyway, every time I invoke the function. And I must be missing something obvious.
我完全期望这样的事情能奏效。但它根本不像我预期的那样工作。似乎无论我做什么,每次调用该函数时,我最终都必须输入默认参数。我一定遗漏了一些明显的东西。
采纳答案by drew010
I would propose changing the function declaration as follows so you can do what you want:
我建议按如下方式更改函数声明,以便您可以执行所需的操作:
function foo($blah, $x = null, $y = null) {
if (null === $x) {
$x = "some value";
}
if (null === $y) {
$y = "some other value";
}
code here!
}
This way, you can make a call like foo('blah', null, 'non-default y value');
and have it work as you want, where the second parameter $x
still gets its default value.
通过这种方式,您可以进行类似的调用foo('blah', null, 'non-default y value');
并让它按照您的意愿工作,其中第二个参数$x
仍然获得其默认值。
With this method, passing a null value means you want the default value for one parameter when you want to override the default value for a parameter that comes after it.
使用此方法,传递空值意味着当您想要覆盖一个参数的默认值时,您需要该参数的默认值。
As stated in other answers,
如其他答案所述,
default parameters only work as the last arguments to the function. If you want to declare the default values in the function definition, there is no way to omit one parameter and override one following it.
默认参数仅用作函数的最后一个参数。如果要在函数定义中声明默认值,则无法省略一个参数并覆盖其后的一个参数。
If I have a method that can accept varying numbers of parameters, and parameters of varying types, I often declare the function similar to the answer shown by Ryan P.
如果我有一个方法可以接受不同数量的参数和不同类型的参数,我通常会声明类似于 Ryan P. 给出的答案的函数。
Here is another example (this doesn't answer your question, but is hopefully informative:
这是另一个示例(这不能回答您的问题,但希望能提供信息:
public function __construct($params = null)
{
if ($params instanceof SOMETHING) {
// single parameter, of object type SOMETHING
} else if (is_string($params)) {
// single argument given as string
} else if (is_array($params)) {
// params could be an array of properties like array('x' => 'x1', 'y' => 'y1')
} else if (func_num_args() == 3) {
$args = func_get_args();
// 3 parameters passed
} else if (func_num_args() == 5) {
$args = func_get_args();
// 5 parameters passed
} else {
throw new InvalidArgumentException("Could not figure out parameters!");
}
}
回答by Ryan P
Optional arguments only work at the end of a function call. There is no way to specify a value for $y in your function without also specifying $x. Some languages support this via named parameters (VB/C# for example), but not PHP.
可选参数仅在函数调用结束时起作用。如果不指定 $x,则无法在函数中为 $y 指定值。某些语言通过命名参数(例如 VB/C#)支持这一点,但 PHP 不支持。
You can emulate this if you use an associative array for parameters instead of arguments -- i.e.
如果您使用关联数组作为参数而不是参数,您可以模拟这一点——即
function foo(array $args = array()) {
$x = !isset($args['x']) ? 'default x value' : $args['x'];
$y = !isset($args['y']) ? 'default y value' : $args['y'];
...
}
Then call the function like so:
然后像这样调用函数:
foo(array('y' => 'my value'));
回答by David
It is actually possible:
其实是可以的:
foo( 'blah', (new ReflectionFunction('foo'))->getParameters()[1]->getDefaultValue(), 'test');
Whether you would want to do so is another story :)
你是否愿意这样做是另一回事:)
UPDATE:
更新:
The reasons to avoid this solution are:
避免使用此解决方案的原因是:
- it is (arguably) ugly
- it has an obvious overhead.
- as the other answers proof, there are alternatives
- 它(可以说)丑陋
- 它有一个明显的开销。
- 作为其他答案的证明,还有其他选择
But it can actually be useful in situations where:
但它实际上在以下情况下很有用:
- you don't want/can't change the original function.
you could change the function but:
- using
null
(or equivalent) is not an option (see DiegoDD's comment) - you don't want to go either with an associative or with
func_num_args()
- your life depends on saving a couple of LOCs
- using
- 你不想/不能改变原来的功能。
您可以更改功能,但是:
- 使用
null
(或等效的)不是一个选项(见 DiegoDD 的评论) - 你不想与关联或与
func_num_args()
- 你的生命取决于保存几个 LOC
- 使用
About the performance, a very simple testshows that using the Reflection API to get the default parameters makes the function call 25 times slower, while it still takes less than one microsecond. You should know if you can to live with that.
关于性能,一个非常简单的测试表明,使用Reflection API获取默认参数使得函数调用速度慢了25倍,同时仍然不到一微秒。你应该知道你是否可以忍受它。
Of course, if you mean to use it in a loop, you should get the default value beforehand.
当然,如果你打算在循环中使用它,你应该事先获得默认值。
回答by zloctb
function image(array $img)
{
$defaults = array(
'src' => 'cow.png',
'alt' => 'milk factory',
'height' => 100,
'width' => 50
);
$img = array_merge($defaults, $img);
/* ... */
}
回答by Wes Crow
The only way I know of doing it is by omitting the parameter. The only way to omit the parameter is to rearrange the parameter list so that the one you want to omit is after the parameters that you HAVEto set. For example:
我知道的唯一方法是省略参数。省略该参数的唯一方法是重新排列参数列表,让你想省略的一个参数后,你HAVE进行设置。例如:
function foo($blah, $y = "some other value", $x = "some value")
Then you can call foo like:
然后你可以像这样调用 foo:
foo("blah", "test");
This will result in:
这将导致:
$blah = "blah";
$y = "test";
$x = "some value";
回答by Yehosef
I recently had this problem and found this question and answers. While the above questions work, the problem is that they don't show the default values to IDEs that support it (like PHPStorm).
我最近遇到了这个问题,并找到了这个问题和答案。虽然上述问题有效,但问题在于它们没有向支持它的 IDE(如 PHPStorm)显示默认值。
if you use null
you won't know what the value would be if you leave it blank.
如果您使用,null
您将不知道如果将其留空,该值会是多少。
The solution I prefer is to put the default value in the function definition also:
我更喜欢的解决方案是将默认值也放在函数定义中:
protected function baseItemQuery(BoolQuery $boolQuery, $limit=1000, $sort = [], $offset = 0, $remove_dead=true)
{
if ($limit===null) $limit =1000;
if ($sort===null) $sort = [];
if ($offset===null) $offset = 0;
...
The only difference is that I need to make sure they are the same - but I think that's a small price to pay for the additional clarity.
唯一的区别是我需要确保它们是相同的 - 但我认为这是为额外的清晰度付出的一个很小的代价。
回答by kba
You can't do this directly, but a little code fiddling makes it possible to emulate.
您不能直接执行此操作,但是稍微摆弄代码就可以进行模拟。
function foo($blah, $x = false, $y = false) {
if (!$x) $x = "some value";
if (!$y) $y = "some other value";
// code
}
回答by Odin
<?php
function info($name="George",$age=18) {
echo "$name is $age years old.<br>";
}
info(); // prints default values(number of values = 2)
info("Nick"); // changes first default argument from George to Nick
info("Mark",17); // changes both default arguments' values
?>
回答by Roger
Pass an array to the function, instead of individual parameters and use null coalescing operator (PHP 7+).
将数组传递给函数,而不是单个参数并使用空合并运算符(PHP 7+)。
Below, I'm passing an array with 2 items. Inside the function, I'm checking if value for item1 is set, if not assigned default vault.
下面,我传递了一个包含 2 个项目的数组。在函数内部,我正在检查是否设置了 item1 的值,如果未分配默认保险库。
$args = ['item2' => 'item2',
'item3' => 'value3'];
function function_name ($args) {
isset($args['item1']) ? $args['item1'] : 'default value';
}