Hi there everyone!

I've written a function to find recursive categories and for finding them, it's working well. The issue I'm having is that it's nesting the child categories in the array and I need them to all be on the same dimension.

Function:

function cat_array($parent, $level){
	global $link;
	$q_cats = "SELECT * FROM categories WHERE parent = '$parent' ORDER BY name ASC";
	$r_cats = mysqli_query ($link, $q_cats) or die('Catastrophic failure [Super secret code 95162]');
	$num_cats=mysqli_num_rows($r_cats);
	if($num_cats != 0){
		while ($row_cats = mysqli_fetch_assoc ($r_cats)) {
			$cat_id = $row_cats['id'];
			$name = $row_cats['name'];
			$safename = $row_cats['safename'];
			$parent = $row_cats['parent'];
			$catcounter = mysqli_query($link, "SELECT COUNT(*) AS id FROM links WHERE category = '$cat_id'");
			$catnum = mysqli_fetch_array($catcounter);
			$catcount = number_format($catnum["id"]);

		$cat_array = array("id"=>$cat_id, "name"=>$name, "safename"=>$safename, "parent"=>$parent, "linkcount"=>$catcount, "level"=>$level);

		/* This is supposed to use the function again inside this loop to find the children of the current row */
		$cat_array3[] = cat_array($cat_id, $level+1);

		/* If the child loop isn't empty, merge them. */
		if(!empty($cat_array3)){
			$cat_array4[] = array_merge($cat_array, $cat_array3);
		}

		/* Wiping the temp arrays */
		UNSET($cat_array);
		UNSET($cat_array2);
		UNSET($cat_array3);


	}
	/* Placed inside the count check so it doesn't return anything if nothing found */
	$cat_array = $cat_array4;
	return $cat_array;
}

}

Instead of my array nesting results, such as: [0][0], [0][1], [0][1][0], [0][2]

I would like [0], [1], [2], [3], [4], [5]

The array looks like this:

Array
(
    [0] => Array
        (
            [0] => Array
                (
                    [id] => 1
                    [name] => ALTERNATOR, BATTERY & CHARGING
                    [safename] => alternator-battery-and-charging
                    [description] => 3G, Dual batteries, isolators and more
                    [parent] => 0
                    [linkcount] => 0
                    [level] => 0
                )

        [1] => Array
            (
                [0] => Array
                    (
                        [0] => Array
                            (
                                [id] => 3
                                [name] => ALTERNATOR
                                [safename] => alternator
                                [description] => 
                                [parent] => 1
                                [linkcount] => 0
                                [level] => 1
                            )

                        [1] => Array
                            (
                                [0] => Array
                                    (
                                        [0] => Array
                                            (
                                                [id] => 35
                                                [name] => Loose or Weak Contact at Generator Harness Connector TSB 96-21-4 for 86-93 Bronco
                                                [safename] => loose-or-weak-contact-at-generator-harness-connector-tsb-96-21-4-for-86-93-bronco
                                                [description] => 
                                                [parent] => 3
                                                [linkcount] => 0
                                                [level] => 2
                                            )

                                        [1] => 
                                    )

                                [1] => Array
                                    (
                                        [0] => Array
                                            (
                                                [id] => 36
                                                [name] => No Crank, Low State Of Battery Charge TSB 91-10-8 for 85-91 Bronco, Bronco II, Econoline, F-150-350 Series, Ranger; 86-91 Aerostar; 88-91 F Super Duty, F47, F-53, F-59; 91 Explorer, etc.
                                                [safename] => no-crank-low-state-of-battery-charge-tsb-91-10-8-for-85-91-bronco-bronco-ii-econoline-f-150-350-series-ranger-86-91-aerostar-88-91-f-super-duty-f47-f-53-f-59-91-explorer-etc-
                                                [description] => 
                                                [parent] => 3
                                                [linkcount] => 0
                                                [level] => 2
                                            )

                                        [1] => 
                                    )

                            )

                    )

                [1] => Array
                    (
                        [0] => Array
                            (
                                [id] => 4
                                [name] => BATTERY & ISOLATOR
                                [safename] => battery-and-isolator
                                [description] => 
                                [parent] => 1
                                [linkcount] => 0
                                [level] => 1
                            )

                        [1] => 
                    )

                [2] => Array
                    (
                        [0] => Array
                            (
                                [id] => 5
                                [name] => GENERAL INFORMATION
                                [safename] => general-information
                                [description] => 
                                [parent] => 1
                                [linkcount] => 0
                                [level] => 1
                            )

                        [1] => 
                    )

            )

    )

[1] => Array
    (
        [0] => Array
            (
                [id] => 2
                [name] => AUDIO AND VIDEO
                [safename] => audio-and-video
                [description] => CBs, antennas, radios and amps
                [parent] => 0
                [linkcount] => 0
                [level] => 0
            )

        [1] => 
    )

[2] => Array
    (
        [0] => Array
            (
                [id] => 6
                [name] => BODY
                [safename] => body
                [description] => Paint, repairs, tailgate and wiring
                [parent] => 0
                [linkcount] => 0
                [level] => 0
            )

        [1] => 
    )
)
)

The nested results are making looping through the array a nightmare. I'd really like the function to append the results to the end of the array without nesting the child results as a child array. Is this possible?

    Solved:

    function cat_array($parent, $level){
    	$go = 1;
    	global $link;
    	if(!ISSET($cat_array)){
    		$cat_array = array();
    	}
    	$q_cats = "SELECT * FROM categories WHERE parent = '$parent' ORDER BY name ASC";
    	$r_cats = mysqli_query ($link, $q_cats) or die('Catastrophic failure [Super secret code 95162]');
    	$num_cats=mysqli_num_rows($r_cats);
    	if($num_cats != 0){
    		while ($row_cats = mysqli_fetch_assoc ($r_cats)) {
    			$cat_id = $row_cats['id'];
    			$name = $row_cats['name'];
    			$safename = $row_cats['safename'];
    			$parent = $row_cats['parent'];
    			$catcounter = mysqli_query($link, "SELECT COUNT(*) AS id FROM links WHERE category = '$cat_id'");
    			$catnum = mysqli_fetch_array($catcounter);
    			$catcount = number_format($catnum["id"]);
    
    		$cat_array1[] = array("id"=>$cat_id, "name"=>$name, "safename"=>$safename, "parent"=>$parent, "linkcount"=>$catcount, "level"=>$level);
    
    		$cat_array = array_merge($cat_array, $cat_array1);
    
    		/* This is supposed to use the function again inside this loop to find the children of the current row */
    		$cat_array3 = cat_array($cat_id, $level+1);
    
    		if(ISSET($cat_array3) AND !empty($cat_array3)){
    			$cat_array = array_merge($cat_array, $cat_array3);
    		}
    
    	}
    
    }
    return $cat_array;
    }

      Another question is why are you running a query in a loop? I'd think the two queries could be combined fairly easily to give the results you're looking for. This hasn't been tested at all, but something like:

      SELECT	 c.*
      	,COUNT(l.*) AS ct
      FROM categories c
      LEFT JOIN links l
      	ON c.id = l.category
      WHERE c.parent = $parent
      GROUP BY l.category

      should get you to the desired result set with a lot less resource use, unless I'm reading something incorrectly. Or just even more brain-fried than I think I am, which admittedly is very possible...

        Write a Reply...