I'm trying to get a multidimensional array comparing the [id] values with the [parent_id] values from an array like this:
Array
(
[0] => Array
(
[id] => 101
[title] => parent_101
[parent_id] => 0
[level] => 1
)
[1] => Array
(
[id] => 118
[title] => parent_118
[parent_id] => 0
[level] => 1
)
[2] => Array
(
[id] => 119
[title] => child_119
[parent_id] => 118
[level] => 2
)
[4] => Array
(
[id] => 173
[title] => subchild_173
[parent_id] => 119
[level] => 3
)
[5] => Array
(
[id] => 120
[title] => child_120
[parent_id] => 118
[level] => 2
)
[6] => Array
(
[id] => 145
[title] => deeperchild_145
[parent_id] => 173
[level] => 4
)
)
The result should be a new array like this:
Array
(
[0] => Array
(
[title] => parent_101
[id] => 101
[parent_id] => 1
[level] => 1
[childrens] => Array
(
)
)
[1] => Array
(
[id] => 118
[title] => parent_118
[parent_id] => 1
[level] => 1
[childrens] => Array
(
[0] => Array
(
[id] => 119
[title] => child_119
[parent_id] => 118
[level] => 2
[deeper] => Array
(
[0] => Array
(
[id] => 173
[title] => subchild_173
[parent_id] => 119
[level] => 3
[deeperchild] => Array
(
[id] => 145
[title] => deeperchild_145
[parent_id] => 173
[level] => 4
)
)
)
)
[1] => Array
(
[id] => 120
[title] => parent_120
[parent_id] => 118
[level] => 2
[deeper] => Array
(
)
)
)
)
)
so far I come up with this code but I'm stuck at the 3rd level deeper and I was wondering if there is a better way to do that.
> $parentsitms = array(); $deeperArr = array(); $childsArr = array();
> $childparent = array(); $menu = array();
>
> foreach ($list as $items) {
>
> if($items->level==='1'):
> $idparent = $items->id;
> $parents = $items->title;
> $parentsitms[] = ['id'=>$items->id,'title'=>$items->title,'parent_id'=>$items->parent_id,'level'=>$items->level];
>
> endif;
>
> }
> foreach ($parentsitms as $menuitm) {
> $parents = $menuitm;
>
> foreach($list as $chd){
>
> if($menuitm['id'] === $chd->parent_id):
> $childparent = $chd->id;
> $childsItms = ['id'=>$chd->id,'title'=>$chd->title,'parent_id'=>$chd->parent_id,'level'=>$chd->level];
> $childsArr[] = [array_merge($childsItms,array('deeper'=>array()))];
> endif;
>
> if($childparent === $chd->parent_id):
> $array = ['title'=>$chd->title,'id'=>$chd->id,'parent_id'=>$chd->parent_id,'level'=>$chd->level];
> $deeperArr[] = ['id'=>$chd->id,'title'=>$chd->title,'parent_id'=>$chd->parent_id,'level'=>$chd->level];
> $childsArr = [array_merge($childsItms,array('deeper'=>$deeperArr))];
> endif;
>
> ######## can't get the 4th level deeper ######
>
>
> }
>
> $menu[] = array_merge($parents,array('childrens'=>$childsArr));
> }
>
> echo '<pre>'; print_r($menu);
Any help is very appreciated.
This code uses a non-recursive method which is a more common method of solving this type of problem. I prefer this method as it makes just one pass through the data and can be easier to follow through (IMHO).
I've added comments to the code as it's easier to describe with the code. The only thing I would say is that this always uses children as the name of the child elements and not the way you do this at the moment...
// Order array so that they are in order of level
usort($list, function ( $a, $b ) { return $a['level'] <=> $b['level']; });
// Create start point with all of the items indexed by their ID
$output = array_column($list, null, "id");
// Work in reverse order
foreach ( array_reverse(array_column($list, "id")) as $id ) {
$parent = $output[$id]['parent_id'];
// If there is a parent to work with
if ( $parent != 0 ) {
// Ensure that the add point is there
if ( !isset($output[$parent]['children']) ) {
$output[$parent]['children'] = [];
}
// Prepend the new item to the list (do this as the items
// are added in reverse oder)
array_unshift($output[$parent]['children'], $output[$id]);
// Remove the old node from the base list
unset($output[$id]);
}
}
$output = array_values($output);
print_r($output);
gives...
Array
(
[0] => Array
(
[id] => 101
[title] => parent_101
[parent_id] => 0
[level] => 1
)
[1] => Array
(
[id] => 118
[title] => parent_118
[parent_id] => 0
[level] => 1
[children] => Array
(
[0] => Array
(
[id] => 119
[title] => child_119
[parent_id] => 118
[level] => 2
[children] => Array
(
[0] => Array
(
[id] => 173
[title] => subchild_173
[parent_id] => 119
[level] => 3
[children] => Array
(
[0] => Array
(
[id] => 145
[title] => deeperchild_145
[parent_id] => 173
[level] => 4
)
)
)
)
)
[1] => Array
(
[id] => 120
[title] => child_120
[parent_id] => 118
[level] => 2
)
)
)
)
Related
Can't get normal tree of comments from database:
Function in model to get data (I use Codeigniter)
public function get_test()
{
$query = $this->db->get('test');
$dataset = $query->result_array();
foreach($dataset as &$row) {
if (!$row['parent_id']) {
$tree[$row['id']] = &$row;
} else {
$tree[$row['parent_id']]['children'][$row['id']] = &$row;
}
}
return $tree;
}
<? echo '<pre>';
print_r($test);
echo '</pre>'; ?>
And this is what I get:
Array
(
[1] => Array
(
[id] => 1
[parent_id] => 0
[name] => Маша
[comment] => Привет всем
[children] => Array
(
[2] => Array
(
[id] => 2
[parent_id] => 1
[name] => Саша
[comment] => И тебе првиет
)
)
)
[3] => Array
(
[id] => 3
[parent_id] => 0
[name] => Даша
[comment] => Ауау
[children] => Array
(
[4] => Array
(
[id] => 4
[parent_id] => 3
[name] => Паша
[comment] => Читай
)
)
)
[2] => Array
(
[children] => Array
(
[5] => Array
(
[id] => 5
[parent_id] => 2
[name] => Петя
[comment] => Еще привет
)
)
)
)
The last array It must be a response to a comment in the first array....What is the problem? I can't find a mistake.
Check again your database maybe by using phpmyadmin because as i saw from the printed array the comment with [id] => 5 has [parent_id] => 2. If you want to display it as child of the comment with [id] => 1 you have to give him the [parent_id] => 1
I want to convert this array in a single dimensional flat array without losing the sort order.
Array
(
[0] => Array
(
[id] => 1
[title] => Computer
[parent_id] => 0
[children] => Array
(
[0] => Array
(
[id] => 4
[title] => keyboard
[parent_id] => 1
[children] => Array
(
[0] => Array
(
[id] => 6
[title] => Mouse
[parent_id] => 4
[children] => Array
(
[0] => Array
(
[id] => 7
[title] => webcam
[parent_id] => 6
)
)
)
)
)
)
)
[1] => Array
(
[id] => 43
[title] => Mobile
[parent_id] => 0
[children] => Array
(
[0] => Array
(
[id] => 5
[title] => bar phones
[parent_id] => 43
)
[1] => Array
(
[id] => 47
[title] => Touchscreen
[parent_id] => 43
[children] => Array
(
[0] => Array
(
[id] => 41
[title] => Samsung
[parent_id] => 47
)
[1] => Array
(
[id] => 44
[title] => Micromax
[parent_id] => 47
)
[2] => Array
(
[id] => 45
[title] => Huawei
[parent_id] => 47
)
)
)
)
)
[2] => Array
(
[id] => 46
[title] => Camera
[parent_id] => 0
)
[3] => Array
(
[id] => 42
[title] => Heater
[parent_id] => 0
)
)
Give it try with below function:
function makeOneDimensionArray(array $array, &$res = array())
{
foreach($array as $arr)
{
$res[] = array(
'id' => $arr['id'],
'title' => $arr['title'],
'parent_id' => $arr['parent_id']
);
if(isset($arr['children']))
{
makeOneDimensionArray($arr['children'], $res);
}
}
return $res;
}
$finalArr = makeOneDimensionArray($your_array);
print_r($finalArr);
I have one array in php like this :
Array
(
[0] => Array
(
[name] => abc
[id] => 107
[CycleNumber] => 1
[Type] => People
)
[1] => Array
(
[name] => john
[id] => 312
[CycleNumber] => 5
[Type] => People
)
[2] => Array
(
[name] => jenny
[id] => 110
[CycleNumber] => 3
[Type] => People
)
[3] => Array
(
[name] => metting room
[id] => 590
[CycleNumber] => 4
[Type] => Facility
)
[4] => Array
(
[name] => projector
[id] => 470
[CycleNumber] => 4
[Type] => Facility
)
)
I want to replace the duplicate type with blank. but the first one should have that type name and others should have blank. so the result array should be like this :
Array
(
[0] => Array
(
[name] => abc
[id] => 107
[CycleNumber] => 1
[Type] => People
)
[1] => Array
(
[name] => john
[id] => 312
[CycleNumber] => 5
[Type] =>
)
[2] => Array
(
[name] => jenny
[id] => 110
[CycleNumber] => 3
[Type] =>
)
[3] => Array
(
[name] => metting room
[id] => 590
[CycleNumber] => 4
[Type] => Facility
)
[4] => Array
(
[name] => projector
[id] => 470
[CycleNumber] => 4
[Type] =>
)
)
I want array in this format only. and i am using PHP zend.
I search for this but most of them showing to remove that element from array. but i don't want to remove it. i want to replace it with blank but want to show the first one.
Tried Code
$result = array();
$result1 = array();
$result2 = array();
$y = array();
$y1 = array();
foreach ($data as $entry) {
$type= $entry["type"];
if (!isset($y[$type])) {
$y[$type] = array();
unset($entry["type"]);
$result[$type][] = $entry;
}
}
can anyone tell me how to do that ?
Code
$i = 0;
$found = 0;
foreach($data as $key=>&$val) {
if($i != 0) {
if($data[$i]['Type'] == $data[$found]['Type']) {
$data[$i]['Type'] = "";
}
else {
$found = $i;
}
}
$i++;
}
echo "<pre>";
print_r($data);
Output
Array
(
[0] => Array
(
[name] => abc
[id] => 107
[CycleNumber] => 1
[Type] => People
)
[1] => Array
(
[name] => john
[id] => 312
[CycleNumber] => 5
[Type] =>
)
[2] => Array
(
[name] => jenny
[id] => 110
[CycleNumber] => 3
[Type] =>
)
[3] => Array
(
[name] => metting room
[id] => 590
[CycleNumber] => 4
[Type] => Facility
)
[4] => Array
(
[name] => projector
[id] => 470
[CycleNumber] => 4
[Type] =>
)
)
Example
Its generally related to a question in magento ..but i think using core php can also give me a wat i want
Im having a looping array issue here,My aray is like this
Array
(
[0] => Array
(
[category_id] => 2
[parent_id] => 1
[name] => Koffersenkisten
[is_active] => 0
[position] => 1
[level] => 1
[children] => Array
(
[0] => Array
(
[category_id] => 40
[parent_id] => 2
[name] => Muziek
[is_active] => 1
[position] => 1
[level] => 2
[children] => Array
(
[0] => Array
(
[category_id] => 46
[parent_id] => 40
[name] => Gitaar koffer
[is_active] => 1
[position] => 1
[level] => 3
[children] => Array
(
[0] => Array
(
[category_id] => 50
[parent_id] => 46
[name] => Bas gitaar koffer
[is_active] => 1
[position] => 1
[level] => 4
[children] => Array
(
)
)
[1] => Array
(
[category_id] => 51
[parent_id] => 46
[name] => Electrische gitaar koffer
[is_active] => 1
[position] => 2
[level] => 4
[children] => Array
(
)
)
[2] => Array
(
[category_id] => 47
[parent_id] => 46
[name] => Akoestische gitaar koffer
[is_active] => 1
[position] => 3
[level] => 4
[children] => Array
(
)
)
[3] => Array
(
[category_id] => 49
[parent_id] => 46
[name] => Gitaar soft cases
[is_active] => 1
[position] => 4
[level] => 4
[children] => Array
(
)
)
[4] => Array
(
[category_id] => 52
[parent_id] => 46
[name] => Gitaar gig bags
[is_active] => 1
[position] => 5
[level] => 4
[children] => Array
(
)
)
[5] => Array
(
[category_id] => 53
[parent_id] => 46
[name] => Pedalboards
[is_active] => 1
[position] => 6
[level] => 4
[children] => Array
(
)
)
[6] => Array
(
[category_id] => 48
[parent_id] => 46
[name] => Amp Utility Vehicles
[is_active] => 1
[position] => 7
[level] => 4
[children] => Array
(
)
)
)
)
[1] => Array
(
[category_id] => 67
[parent_id] => 40
[name] => Percussie koffer
[is_active] => 1
[position] => 2
[level] => 3
[children] => Array
(
[0] => Array
(
[category_id] => 73
[parent_id] => 67
[name] => Tom koffer
[is_active] => 1
[position] => 1
[level] => 4
[children] => Array
(
)
)
.......
......
>> it goes like this based on the number of categories
How do i get a simple array of the above like this
array('2' => 'Koffersenkisten','40'=> 'Muziek'...........etc); where 2 is the category_id and Koffersenkisten is the name
This function iterates over all items, and recurses when children are found. It passes the output array along at every invocation and appends to it:
function get_cats(array &$output, array $arr)
{
foreach ($arr as $item) {
$output[$item['category_id']] = $item['name'];
if (count($item['children'])) {
get_cats($output, $item['children']);
}
}
}
// start with empty result
$output = array();
get_cats($output, $a);
print_r($output);
This should work. Didn't test it.
$result = array();
function buildArray($array, $stack)
{
foreach($array as $item)
{
$stack[$item['category_id']] = $item['name'];
if(isset($item['children']) && count($item['children']) > 0)
foreach($item['children'] as $child)
buildArray($item['children'], &$stack);
}
}
buildArray($array, &$result);
print_r($result);
Here is a recursive solution (the array should be in $list before, the created array will be in $result after calling the create function):
function create($list, &$result) {
if (is_array($list) && !isset($list['category_id'])) {
foreach ($list as $element) {
create($element, $result);
}
} else {
$result[$list['category_id']] = $list['name'];
create($list['children'], $result);
}
}
create($list, $result);
Also see this example.
I have this array:
$items_pool = Array (
[0] => Array ( [id] => 1 [quantity] => 1 )
[1] => Array ( [id] => 2 [quantity] => 1 )
[2] => Array ( [id] => 72 [quantity] => 6 )
[3] => Array ( [id] => 4 [quantity] => 1 )
[4] => Array ( [id] => 5 [quantity] => 1 )
[5] => Array ( [id] => 7 [quantity] => 1 )
[6] => Array ( [id] => 8 [quantity] => 1 )
[7] => Array ( [id] => 9 [quantity] => 1 )
[8] => Array ( [id] => 19 [quantity] => 1 )
[9] => Array ( [id] => 20 [quantity] => 1 )
[10] => Array ( [id] => 22 [quantity] => 1 )
[11] => Array ( [id] => 29 [quantity] => 0 )
)
I'm trying to loop through this array and perform a conditional based on $items_pool[][id]'s value. I want to then report back TRUE or NULL/FALSE, so I'm just testing the presence of to be specific.
Something like this:
$items_pool = array(...);
$result = false;
foreach ($items_pool as $item) {
if ('something' == $item['id']) {
$result = true;
break;
}
}
Loop through an check if anything is empty..
foreach($items_pool as $arr){
echo $arr['id'].'==>'.$arr['quantity'];
if($arr['quantity'] == 0){
echo 'id:'.$arr['id'].' is empty!';
return false;
}
}