usort改变数组顺序

5

我有一个只有一行代码的usort函数:return 0。我尝试在stdClass对象数组上使用它,结果改变了它们的顺序,这是怎么可能的?


尝试使用uasort,仍然改变了顺序。 - Asaf
将uasort更改为usort,它仍然会改变顺序。 - Asaf
3个回答

11
你所假设的属性称为稳定性:一个稳定的排序算法不会改变相等元素之间的顺序。 php的排序函数不是稳定的(因为非稳定排序可能会稍微快一些)。从usort文档中可以看到:

如果两个成员比较相等,它们在排序后的数组中的顺序是未定义的。

如果你想要一个稳定的排序算法,你必须自己实现

谢谢!顺便说一下(使用PHP 7.1.9):“类型错误:array_slice()期望第二个参数为整数,但给出了浮点数”。使用$halfway = intval(count($array) / 2);似乎可以解决这个问题,但我不确定是否会影响其他东西(将数组精确地切片很重要吗?)。 - fiskhandlarn

1

这是因为该函数的意思是“我真的不在乎它们如何排序,它们对我来说是相等的”。通过这个简单的示例,我收到了反转的数组:

function sortaaa($a,$b) {return 0;}
$array = array(1,2,3,4,5);
usort($array,"sortaaa");
var_dump($array);
//prints array(5) { [0]=> int(5) [1]=> int(4) [2]=> int(3) [3]=> int(2) [4]=> int(1) }

看起来PHP在函数usort中以相反的顺序循环数组。因此,请注意usortmanual中所述:

如果两个成员比较相等,则它们在排序后的数组中的顺序是未定义的。


你会建议什么解决方案? - Asaf
这取决于您所说的解决方案是什么意思。您想要实现什么? - J0HN
@Asaf 如果稳定性是一个问题,那就自己编写排序程序。我在我的回答中添加了一个链接 - phihag

1
如果你正在寻找一个快速且稳定的usort解决方案,你可以像以下示例使用uksort:
<?php

uksort($array, function ($ak, $bk) use ($array) {
    $a = $array[$ak];
    $b = $array[$bk];

    if ($a['foo'] === $b['foo']) 
        return $ak - $bk;

    return $a['foo'] > $b['foo'] ? 1 : -1;
});

只有当$array的初始索引(键)按升序排列时,此功能才能正常工作。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接