我有两个代码片段做同样的事情,但是通过不同的方法,哪一个更好,为什么?非常感谢。第一个处理函数handle()中的$ arr并且不返回值,因为它是pass-by-refference,所有更改都发生在函数handle()中,因此它不需要返回任何值。
第二个片段从函数handle()返回值并覆盖$ arr []中的先前值;
一个不返回而另一个返回,我想知道哪种方法适合或者更喜欢,最重要的是,为什么,谢谢!返回和不返回之间的选择
第二个代码是
代码段A:
class a {
public function org(){
$arr = array(1=>1,2=>2,3=>3);
foreach($arr as $k=>&$v){
$this->handle($v);
}
print_r($arr);
}
public function handle(&$item){
$item+=1;
}
}
$b = new a();
$b->org();
摘录B:
class a {
public function org(){
$arr = array(1=>1,2=>2,3=>3);
foreach($arr as $k=>$v){
$arr[$k] = $this->handle($v);
}
print_r($arr);
}
public function handle($item){
return $item+=1;
}
}
$b = new a();
$b->org();
答案 0 :(得分:1)
通过引用接受其参数并就地修改它们的函数( mutators )通常(但不总是!)更有效。这是因为他们不需要消耗内存和CPU周期来制作他们的参数副本 - 他们将对参数本身进行操作。
处理其参数并返回结果值而不修改原始值(变换器)的函数更灵活,更方便使用。
公平地说,我还应该提一下,如果函数想要报告可能的失败,那么变换器就更难了,因为它们已经返回结果(另一方面,mutators可以自由使用)为此目的的返回值)。但是,这种错误检查方式今天不受欢迎,通常不推荐。
作为一个说明性示例,让我们比较函数shuffle
和array_unique
。它们都在阵列上运行,但第一个是变换器,而第二个是变换器。假设我们想要计算通过每个数组传递数组的结果:
$count = count(array_unique($array)); // convenient one-liner
shuffle($array);
$count = count($array); // two statements necessary: shuffle cannot be chained
示例是设计的,但如果array_unique
和shuffle
是同一功能的不同实现,您显然更愿意在源代码中使用array_unique
。
现在让我们通过比较sort
的mutator和变换器版本的资源使用情况,看看mutators如何比变换器更高效:
的Mutator:
$array = range(1, 10000);
shuffle($array);
sort($array);
$oneToTen = array_slice($array, 0, 10);
echo memory_get_peak_usage();
<强> See it in action 强>
变压器:
function transformer_sort($array)
{
sort($array);
return $array;
}
$array = range(1, 10000);
shuffle($array);
$oneToTen = array_slice(transformer_sort($array), 0, 10);
echo memory_get_peak_usage();
<强> See it in action 强>
正如您所看到的,mutator版本总共需要更少的内存来达到相同的结果。但是有一个权衡:代码不太方便,它“破坏”我们的初始数据数组。如果我们需要保留初始数据,那么内存使用量将是相同的,从而消除了mutator的优势并使其处于劣势。
我建议遵循以下经验法则:
编写函数时,总是将它变为变换器而不是第一个变换器 选择。强>
如果您遇到性能问题,可以通过分析来证明 应用程序,这些问题可以通过使用mutator来解决 而不是变压器,用等效的替换那些变压器 存取器。
答案 1 :(得分:0)
最好的是:):
$arr[$k] = $v + 1;
否则 - 我假设您的代码只是一个示例 - 我建议使用函数的返回值(SnippetB)而不是通过引用传递。如果示例不那么简单,那就是返回值的目的和通过引用传递可能会产生意想不到的副作用。
答案 2 :(得分:0)
最简单的就是hek2mgl所说的。但是如果你只是想知道原因,那是因为你创建另一个函数不仅会增加你正在使用的内存中的堆栈,还需要一个额外的CPU步骤来调用该函数。
另外,对于返回值的函数,PHP必须创建一个临时变量来保存并返回值。因此,您实际上暂时在内存中复制数据。
但说实话,除非你的移动阵列长达数百万加,你不会看到太大的差别。我会说这两个功能在足迹方面几乎完全相同。
答案 3 :(得分:0)
要考虑的第三个选项,请记住数组永远不会离开类:
class a {
private $arr;
public function __construct() {
$this->arr = array(1=>1,2=>2,3=>3);
}
public function org() {
$this->handle();
print_r($this->arr);
}
public function handle() {
foreach(array_keys($this->arr) as $k){
$this->arr[$k]++;
}
}
}
如果数组是类的属性,则不需要通过值或引用传递它。
答案 4 :(得分:0)
避免像你一样通过引用传递,避免使用&amp;,这被认为是一种不好的做法。您可以像第二个示例代码一样返回该值。
为什么呢?因为如果你有很多参考资料,改变另一个参考资料将很难追踪发生的事情。
请记住,默认情况下,对象始终通过引用传递。