php - 按多个字段对多维数组进行排序
问题描述
我发现了一些关于这个的问题,但我觉得我这里有一个非常特殊的情况,所以我要问一个新的。
我需要先按他们的标题(数组)然后按姓氏对用户数组进行排序,请考虑以下代码:
<?php
$users = [
[
'lastName' => 'Clarks',
'titles' => ['Manager', 'Supervisor']
],
[
'lastName' => 'Clarkson',
'titles' => ['Sales']
],
[
'lastName' => 'Adams',
'titles' => ['Supervisor']
],
[
'lastName' => 'Adams',
'titles' => ['Manager', 'Senior Manager']
],
[
'lastName' => 'Clarkson',
'titles' => ['Manager']
],
[
'lastName' => 'Davids',
'titles' => ['Senior Manager']
]
];
我想要的顺序是:
<?php
$order = [
'Senior Manager',
'Manager',
'Supervisor'
];
如果有多个经理,他们应该按姓氏排序,所以这种情况下的输出将是:
<?php
$sorted = [
[
'lastName' => 'Adams',
'titles' => ['Manager', 'Senior Manager']
],
[
'lastName' => 'Davids',
'titles' => ['Senior Manager']
],
[
'lastName' => 'Clarks',
'titles' => ['Manager', 'Supervisor']
],
[
'lastName' => 'Clarkson',
'titles' => ['Manager']
],
[
'lastName' => 'Adams',
'titles' => ['Supervisor']
],
[
'lastName' => 'Clarkson',
'titles' => ['Sales']
]
];
我已经尝试过这些方面的东西,但无法让它工作并且发现它有点难以调试usort
:
<?php
foreach ($order as $title) {
usort($users, function ($a, $b) use ($title) {
# Both have the title
if (in_array($title, $a['titles']) and in_array($title, $b['titles']) ) {
# Sort by name
return strcmp($a['lastName'], $b['lastName']);
}
# A has the title
elseif (in_array($title, $a['titles'])) {
return 1;
}
# B has the title
elseif (in_array($title, $b['titles'])) {
return -1;
}
# No-one has the title
return strcmp($a['lastName'], $b['lastName']);
});
}
解决方案
问题是数组被一遍又一遍地排序。所以如果你在foreach循环中一步一步来,item首先按照高级经理职称排序,然后再按照经理职称排序,最后再按照主管职称排序。
所以首先,你必须颠倒你想要的顺序:
$order = array_reverse([
'Senior Manager',
'Manager',
'Supervisor'
]);
如果它们都没有标题,那么你不想移动它们。因为在您的其他迭代中,您的高级经理可能没有主管头衔,而其他用户也可能没有头衔,因此他们俩都不应更改职位。所以你可以将最后一次返回更改为return 0;
最后,你已经反转了返回,1
所以-1
你只需要切换它们。
最后,最终代码如下所示:
$users = [
[
'lastName' => 'Clarks',
'titles' => ['Manager', 'Supervisor']
],
[
'lastName' => 'Clarkson',
'titles' => ['Sales']
],
[
'lastName' => 'Adams',
'titles' => ['Supervisor']
],
[
'lastName' => 'Adams',
'titles' => ['Manager', 'Senior Manager']
],
[
'lastName' => 'Clarkson',
'titles' => ['Manager']
],
[
'lastName' => 'Davids',
'titles' => ['Senior Manager']
]
];
$order = array_reverse([
'Senior Manager',
'Manager',
'Supervisor'
]);
foreach ($order as $title) {
usort($users, function ($a, $b) use ($title) {
if (in_array($title, $a['titles']) && in_array($title, $b['titles'])) {
return strcmp($a['lastName'], $b['lastName']);
}
# A has the title
elseif (in_array($title, $a['titles'])) {
return -1;
}
# B has the title
elseif (in_array($title, $b['titles'])) {
return 1;
}
return 0;
});
}
输出将是:
array(6) {
[0]=>
array(2) {
["lastName"]=>
string(5) "Adams"
["titles"]=>
array(2) {
[0]=>
string(7) "Manager"
[1]=>
string(14) "Senior Manager"
}
}
[1]=>
array(2) {
["lastName"]=>
string(6) "Davids"
["titles"]=>
array(1) {
[0]=>
string(14) "Senior Manager"
}
}
[2]=>
array(2) {
["lastName"]=>
string(6) "Clarks"
["titles"]=>
array(2) {
[0]=>
string(7) "Manager"
[1]=>
string(10) "Supervisor"
}
}
[3]=>
array(2) {
["lastName"]=>
string(8) "Clarkson"
["titles"]=>
array(1) {
[0]=>
string(7) "Manager"
}
}
[4]=>
array(2) {
["lastName"]=>
string(5) "Adams"
["titles"]=>
array(1) {
[0]=>
string(10) "Supervisor"
}
}
[5]=>
array(2) {
["lastName"]=>
string(8) "Clarkson"
["titles"]=>
array(1) {
[0]=>
string(5) "Sales"
}
}
}
推荐阅读
- php - Laravel - 我如何查询月份和年度日期?
- python - 返回变量名而不是它的值
- ios - Xcode 11.1 未安装带有更改的新版本 (iOS 13.1.2)
- google-apis-explorer - 为什么我不能使用在线 Api Explorer 将现有 MediaItem 添加到现有相册?
- spring-boot - 在springboot中生成YAML格式响应
- mysql - 如何在一个查询中从三个表中获取数据,其中表 2 包含表 1 和表 3 中的外键
- spring-boot - 是否值得在 Spring-boot 应用程序中使用 AOP?
- azure - Azure函数获取http触发器的路径
- python - 如何使用python将我的构建参数作为键和值写入文件
- javascript - 单击另一个音频元素时暂停音频