在PHP中使用多个条件对多维数组排序
我正试图从一个DB查询中建立一个结果数组,基本上我想知道下面的方法是否可行 数组内容:在PHP中使用多个条件对多维数组排序,php,arrays,sorting,multidimensional-array,Php,Arrays,Sorting,Multidimensional Array,我正试图从一个DB查询中建立一个结果数组,基本上我想知道下面的方法是否可行 数组内容: Array ( [0] => Array ( [Section_Id] => 1 [Section_Name] => "Section1" [Section_Parent] => NULL [Section_Position] => 0
Array
(
[0] => Array
(
[Section_Id] => 1
[Section_Name] => "Section1"
[Section_Parent] => NULL
[Section_Position] => 0
[Section_Depth] => 0
)
[1] => Array
(
[Section_Id] => 3
[Section_Name] => "Section2"
[Section_Parent] => NULL
[Section_Position] => 1
[Section_Depth] => 0
)
[2] => Array
(
[Section_Id] => 4
[Section_Name] => "SubSection1ForSection2"
[Section_Parent] => 3
[Section_Position] => 0
[Section_Depth] => 1
)
[3] => Array
(
[Section_Id] => 2
[Section_Name] => "SubSection1ForSection1"
[Section_Parent] => 1
[Section_Position] => 0
[Section_Depth] => 1
)
)
如果您要对这一个进行排序,让我们假设在第_节位置,它将返回如下内容:
usort($sections, function($a, $b) {
return $a['section_position'] - $b['section_position'];
});
(对不起我的英语。)好的,这可能是一个丑陋的解决方案,但如果你把所有东西都放在一个函数中,它看起来很好:)。好的是,它将在您的场景中工作 代码: 注意:第一个排序是根据父节位置进行排序,然后根据子节位置进行排序 U p D A T E 首先,我想对主持人说声抱歉,因为我们与@Akorna进行了长时间的讨论,但我需要给他这个代码,我认为这将在未来起到作用。因此@Akorna应该适用于您的代码如下:
$inputData=数组(
排列(
“截面id”=>333,
“截面深度”=>1,
“节_父项”=>332,
“截面位置”=>0,
“章节标题”=>“引言”),
排列(
“节号”=>334,
“截面深度”=>1,
“节_父项”=>332,
“截面位置”=>1,
“章节标题”=>“词汇表”),
排列(
“截面id”=>335,
“截面深度”=>1,
“节_父项”=>332,
“截面位置”=>2,
'部分标题'=>'命令'),
排列(
“截面id”=>336,
“截面深度”=>1,
“节_父项”=>332,
“截面位置”=>3,
“部分标题”=>“组件”),
排列(
“截面id”=>337,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>0,
“章节标题”=>“引言”),
排列(
“截面id”=>407,
“截面深度”=>2,
“section_parent”=>401,
“截面位置”=>2,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>338,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>1,
“section_title'=>“AbstractContainer”),
排列(
“截面id”=>406,
“截面深度”=>2,
“section_parent”=>401,
“截面位置”=>1,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>339,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>2,
“部分标题”=>“操作容器”),
排列(
“截面id”=>340,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>3,
“章节标题”=>“浏览器不兼容”),
排列(
“截面id”=>404,
“截面深度”=>2,
“节_父项”=>402,
“截面位置”=>3,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>341,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>4,
“节标题”=>“可折叠容器”),
排列(
“截面id”=>342,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>5,
“章节标题”=>“详细信息容器”),
排列(
“截面id”=>343,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>6,
“部分标题”=>“动态菜单”),
排列(
“节号”=>403,
“截面深度”=>2,
“节_父项”=>402,
“截面位置”=>1,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>344,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>7,
“部分标题”=>“设置”),
排列(
“截面id”=>345,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>8,
“章节标题”=>“子文件视图”),
排列(
“截面id”=>346,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>9,
“章节标题”=>“分类管理”),
排列(
“截面id”=>402,
“截面深度”=>1,
“节_父项”=>400,
“截面位置”=>2,
“部分标题”=>“Web应用程序”),
排列(
'截面id'=>401,
“截面深度”=>1,
“节_父项”=>400,
“截面位置”=>1,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>347,
“截面深度”=>2,
“节_父项”=>336,
“截面位置”=>10,
“section_title'=>“UploadQueue”),
排列(
“截面id”=>400,
“截面深度”=>0,
“section_parent”=>null,
“截面位置”=>5,
“部分标题”=>“Web应用程序”),
排列(
“截面id”=>332,
“截面深度”=>0,
“section_parent”=>null,
“截面位置”=>3,
'部分标题'=>'Web应用程序')
);
/*先按截面深度排序,然后按截面位置排序*/
$inputData=array\u orderby($inputData,'section\u depth',SORT\u ASC,'section\u position',SORT\u ASC);
$parents=array();
$sortedByParent=false;
而(!$sortedByParent){
$elems=阵列拼接($inputData,count($inputDat
$inputData = array(
array(
'Section_Id' => 1,
'Section_Name' => "Section1",
'Section_Parent' => NULL,
'Section_Position' => 1,
'Section_Depth' => 0,
),
array(
'Section_Id' => 2,
'Section_Name' => "Section2",
'Section_Parent' => NULL,
'Section_Position' => 0,
'Section_Depth' => 0
),
array(
'Section_Id' => 4,
'Section_Name' => "SubSection2ForSection2",
'Section_Parent' => 2,
'Section_Position' => 1,
'Section_Depth' => 1
),
array(
'Section_Id' => 5,
'Section_Name' => "SubSection1ForSection2",
'Section_Parent' => 2,
'Section_Position' => 0,
'Section_Depth' => 1
),
array(
'Section_Id' => 3,
'Section_Name' => "SubSection1ForSection1",
'Section_Parent' => 1,
'Section_Position' => 0,
'Section_Depth' => 1
)
);
$parentRecords = array();
$childRecords = array();
$sorted = array();
/* split in two collections */
foreach ($inputData as $sectionData) {
if (is_null($sectionData['Section_Parent'])) {
/* assume this is a parent */
$parentRecords[] = $sectionData;
} else {
/* assume we are on child row */
$childRecords[] = $sectionData;
}
}
/* now first order parents by Section_Position */
usort($parentRecords, function($a, $b) {
if ($a['Section_Position'] == $b['Section_Position']) {
return 0;
}
return $a['Section_Position'] > $b['Section_Position'] ? 1 : -1;
});
/* now the actual sorting */
foreach ($parentRecords as $parentData) {
$parentId = $parentData['Section_Id'];
/* now get all children of this parent */
$parentChildren = array();
foreach ($childRecords as $childData) {
if ($childData['Section_Parent'] == $parentId) {
$parentChildren[] = $childData;
}
}
/* now sort the children by Section_Position */
usort($parentChildren, function($a, $b) {
if ($a['Section_Position'] == $b['Section_Position']) {
return 0;
}
return $a['Section_Position'] > $b['Section_Position'] ? 1 : -1;
});
$sorted[] = $parentData;
$sorted = array_merge($sorted, $parentChildren);
}
echo '<pre>' . print_r($sorted, true) . '</pre>';
exit;
Array
(
[0] => Array
(
[Section_Id] => 2
[Section_Name] => Section2
[Section_Parent] =>
[Section_Position] => 0
[Section_Depth] => 0
)
[1] => Array
(
[Section_Id] => 5
[Section_Name] => SubSection1ForSection2
[Section_Parent] => 2
[Section_Position] => 0
[Section_Depth] => 1
)
[2] => Array
(
[Section_Id] => 4
[Section_Name] => SubSection2ForSection2
[Section_Parent] => 2
[Section_Position] => 1
[Section_Depth] => 1
)
[3] => Array
(
[Section_Id] => 1
[Section_Name] => Section1
[Section_Parent] =>
[Section_Position] => 1
[Section_Depth] => 0
)
[4] => Array
(
[Section_Id] => 3
[Section_Name] => SubSection1ForSection1
[Section_Parent] => 1
[Section_Position] => 0
[Section_Depth] => 1
)
)
$inputData = array(
array(
'section_id' => 333,
'section_depth' => 1,
'section_parent' => 332,
'section_position' => 0,
'section_title' => 'Introduction'),
array(
'section_id' => 334,
'section_depth' => 1,
'section_parent' => 332,
'section_position' => 1,
'section_title' => 'Glossary'),
array(
'section_id' => 335,
'section_depth' => 1,
'section_parent' => 332,
'section_position' => 2,
'section_title' => 'Commands'),
array(
'section_id' => 336,
'section_depth' => 1,
'section_parent' => 332,
'section_position' => 3,
'section_title' => 'Components'),
array(
'section_id' => 337,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 0,
'section_title' => 'Introduction'),
array(
'section_id' => 407,
'section_depth' => 2,
'section_parent' => 401,
'section_position' => 2,
'section_title' => 'Web Application'),
array(
'section_id' => 338,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 1,
'section_title' => 'AbstractContainer'),
array(
'section_id' => 406,
'section_depth' => 2,
'section_parent' => 401,
'section_position' => 1,
'section_title' => 'Web Application'),
array(
'section_id' => 339,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 2,
'section_title' => 'ActionsContainer'),
array(
'section_id' => 340,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 3,
'section_title' => 'BrowserIncompatibility'),
array(
'section_id' => 404,
'section_depth' => 2,
'section_parent' => 402,
'section_position' => 3,
'section_title' => 'Web Application'),
array(
'section_id' => 341,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 4,
'section_title' => 'CollapsibleContainer'),
array(
'section_id' => 342,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 5,
'section_title' => 'DetailsContainer'),
array(
'section_id' => 343,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 6,
'section_title' => 'DynamicMenu'),
array(
'section_id' => 403,
'section_depth' => 2,
'section_parent' => 402,
'section_position' => 1,
'section_title' => 'Web Application'),
array(
'section_id' => 344,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 7,
'section_title' => 'Settings'),
array(
'section_id' => 345,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 8,
'section_title' => 'SubfilesViewer'),
array(
'section_id' => 346,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 9,
'section_title' => 'Taxonomy Management'),
array(
'section_id' => 402,
'section_depth' => 1,
'section_parent' => 400,
'section_position' => 2,
'section_title' => 'Web Application'),
array(
'section_id' => 401,
'section_depth' => 1,
'section_parent' => 400,
'section_position' => 1,
'section_title' => 'Web Application'),
array(
'section_id' => 347,
'section_depth' => 2,
'section_parent' => 336,
'section_position' => 10,
'section_title' => 'UploadQueue'),
array(
'section_id' => 400,
'section_depth' => 0,
'section_parent' => null,
'section_position' => 5,
'section_title' => 'Web Application'),
array(
'section_id' => 332,
'section_depth' => 0,
'section_parent' => null,
'section_position' => 3,
'section_title' => 'Web Application')
);
/* first order by section_depth and then by section_position */
$inputData = array_orderby($inputData, 'section_depth', SORT_ASC, 'section_position', SORT_ASC);
$parents = array();
$sortedByParent = false;
while (!$sortedByParent) {
$elems = array_splice($inputData, count($inputData) - 1, 1);
if (!count($elems)) {
$sortedByParent = true;
$inputData = array_merge($inputData, $parents);
continue;
}
$elem = $elems[0];
if ($elem['section_depth'] == 0) {
if (!isset($elem['children'])) {
$elem['children'] = array();
}
$parents[] = $elem;
} else {
$inputData = put_in_parent($elem, $inputData);
}
}
/* now we have $inputData in nice format like
* parent(child, child, child(child, child(child, child)), child(child(child(child)))),
* parent(child, child, child(child, child(child, child)), child(child(child(child))))
* */
$inputData = merge_children_recursively(array_reverse($inputData));
function merge_children_recursively($inputData) {
$children = array();
foreach ($inputData as $row) {
if (isset($row['children'])) {
/* this ksort call is necessary because the key is actually section_position */
ksort($row['children']);
$rowCopy = $row;
unset($rowCopy['children']);
$children[] = $rowCopy;
$children = array_merge($children, merge_children_recursively($row['children']));
} else {
$children[] = $row;
}
}
return $children;
}
function put_in_parent($elem, $inputData) {
foreach ($inputData as $k => $row) {
if ($row['section_id'] == $elem['section_parent']) {
if (!isset($inputData[$k]['children'])) {
$inputData[$k]['children'] = array();
}
$inputData[$k]['children'][$elem['section_position']] = $elem;
break;
}
}
return $inputData;
}
function array_orderby() {
$args = func_get_args();
$data = array_shift($args);
foreach ($args as $n => $field) {
if (is_string($field)) {
$tmp = array();
foreach ($data as $key => $row) {
$tmp[$key] = $row[$field];
}
$args[$n] = $tmp;
}
}
$args[] = &$data;
call_user_func_array('array_multisort', $args);
return array_pop($args);
}
echo '<pre>' . print_r($inputData, true) . '</pre>';
exit;