Home > Blockchain >  Recursively traverse multidimensional associative array and create key path strings
Recursively traverse multidimensional associative array and create key path strings

Time:10-10

I have following multi dimensional associative array, I am trying to recursively traverse it and create array with each element parent tree

Input array:

$user = [
    'profile' => [
        'authkey' => '',
        'publickey' => '',
        'status' => 19
    ],
    'setup' => [
        'profile' => false,
        'contact' => false,
        'payments' => false,
        'subscription' => false
    ],
    'paygateway' => [
        'paypal' => [
            'publickey' =>'',
            'secretkey' => '',
            'testarray' => [
                'key1' => 'value1',
                'key2' => 'value2',
                'key3' => [
                    'key4' => 'level4'
                ]
            ],
            'webhookid' => ''
        ],    
        'stripe' => [
            'publickey' => '',
            'secretkey' => ''
        ]
    ]
];

Required output:

array (
  'profile' => 
  array (
    0 => '[profile][authkey]',
    1 => '[profile][publickey]',
    2 => '[profile][status]',
  ),
  'setup' => 
  array (
    0 => '[setup][profile]',
    1 => '[setup][contacts]',
    2 => '[setup][payments]',
    3 => '[setup][subscriptions]',
  ),
  'paygateway' => 
  array (
    0 => '[paygateway][paypal][publickey]',
    1 => '[paygateway][paypal][secretkey]',
    2 => '[paygateway][paypal][testarray][key1]',
    3 => '[paygateway][paypal][testarray][key2]',
    4 => '[paygateway][paypal][testarray][key3][key4]',
    5 => '[paygateway][paypal][webhookid]',
    6 => '[paygateway][stripe][publickey]',
    7 => '[paygateway][stripe][secretkey]',
  ),
)

What I already have:

The following function that perfectly goes through entire tree of the array:

function testArray($array){
    
    foreach($array as $key => $value){
        
        if(is_array($value)){
            echo "$key <br/>";
            testArray($value);
        }else{
            echo "$key : $value <br/>";
        }   
        
    }
}
testArray($user);

I am unable to figure out how to add up the keys from structure and build the output array.

CodePudding user response:

To preserve the original first level keys, I recommend passing each first level value into the recursive function.

In the recursive function, build the formatted key path string as you conditionally traverse deeper on subarrays. Return the populated key paths on each level and push all deeper populated paths upon ascending the tree.

Regarding the array_push() line, it is being used to individually append all elements from the deeper level's returned result to the current level's result. It could have been written as:
$result = array_merge($result, buildKeyPath($value, "{$path}[$key]"));
but I find data "spreading" with array_push() to be more indicative of the type of process being executed.

Code: (Demo)

function buildKeyPath(array $array, string $path): array
{
    $result = [];
    foreach ($array as $key => $value) {
        if (is_array($value)) {
            array_push($result, ...buildKeyPath($value, "{$path}[$key]"));
        } else {
            $result[] = "{$path}[$key]";
        }
    }
    return $result;
}

foreach ($user as $k => &$v) {
   $v = buildKeyPath($v, "[$k]");
}
var_export($user);
  • Related