PHP - Convert Multidimensional Array to 2D Array with Dot Notation Keys

PHP - Convert multidimensional array to 2D array with dot notation keys

teh codez

$ritit = new RecursiveIteratorIterator(new RecursiveArrayIterator($myArray));
$result = array();
foreach ($ritit as $leafValue) {
$keys = array();
foreach (range(0, $ritit->getDepth()) as $depth) {
$keys[] = $ritit->getSubIterator($depth)->key();
}
$result[ join('.', $keys) ] = $leafValue;
}

output

Array
(
[key1] => value1
[key2.subkey] => subkeyval
[key3] => value3
[key4.subkey4.subsubkey4] => subsubkeyval4
[key4.subkey4.subsubkey5] => subsubkeyval5
[key4.subkey5] => subkeyval5
)

demo: http://codepad.org/YiygqxTM

I need to go, but if you need an explanation of that tomorrow, ask me.

Convert dot syntax like this.that.other to multi-dimensional array in PHP

Try this number...

function assignArrayByPath(&$arr, $path, $value, $separator='.') {
$keys = explode($separator, $path);

foreach ($keys as $key) {
$arr = &$arr[$key];
}

$arr = $value;
}

CodePad

It will loop through the keys (delimited with . by default) to get to the final property, and then do assignment on the value.

If some of the keys aren't present, they're created.

How to get the keys of each level of a multidimensional array in PHP

$ini_config['aaa']['email']['main'] = 'me@name.com';
$ini_config['bbb']['email']['ccc'] = 'you@name.com';
$ini_config['bbb']['phone']['local'] = '800-555-1212';
$ini_config['bbb']['phone']['skype'] = '744-222-1234';
$ini_config['ccc']['phone']['main'] = 'domain.com';
$ini_config['ccc']['domain']['https'] = 'https://www. domain.com';
$ini_config['ccc']['fax'] = '744-222-1237';

function keyPaths(array $array, array $carry = [], string $separator = ''): array {
foreach ($array as $key => $value) {
if (is_array($value)) {
$carry = keyPaths($value, $carry, $separator . $key . '_');
} else {
$carry[] = $separator . $key;
}
}
return $carry;
}

$result = keyPaths($ini_config);

PHP : Implode and get the keys of a multidimensional associative array

You can loop over the array at hand. Now, if the current value is an array, recursively call that array to the function call. On each function call, return an array with key value pairs. When you get the output from your sub-array, attach current key value to all keys of that sub-array returned output.

Snippet:

<?php

function rearrange($array){
$output = [];
foreach($array as $key => $val){
if(is_array($val)){
$out = rearrange($val);
foreach($out as $sub_key => $sub_val){
$output[$key . "." . $sub_key] = $sub_val;
}
}else{
$output[$key] = $val;
}
}

return $output;
}

print_r(rearrange($array));

Demo: https://3v4l.org/40hjK

How to flatten a multidimensional collection (array) to a dot notation version in a macro (Laravel)?

The thing you are trying to do is called transform an multidimensional array to array with dot notation.

You don't need to reinvent the wheel, Laravel have already a helper for it, called array_dot().

The array_dot function flattens a multi-dimensional array into a
single level array that uses "dot" notation to indicate depth:

$array = ['products' => ['desk' => ['price' => 100]]];

$flattened = array_dot($array);

// ['products.desk.price' => 100]

You only need to transform your json to array with json_decode() and then flat it with array_dot() to get an array with dot notation.

How to access and manipulate multi-dimensional array by key names / path?

Assuming $path is already an array via explode (or add to the function), then you can use references. You need to add in some error checking in case of invalid $path etc. (think isset):

$key = 'b.x.z';
$path = explode('.', $key);

Getter


function get($path, $array) {
//$path = explode('.', $path); //if needed
$temp =& $array;

foreach($path as $key) {
$temp =& $temp[$key];
}
return $temp;
}

$value = get($path, $arr); //returns NULL if the path doesn't exist

Setter / Creator

This combination will set a value in an existing array or create the array if you pass one that has not yet been defined. Make sure to define $array to be passed by reference &$array:

function set($path, &$array=array(), $value=null) {
//$path = explode('.', $path); //if needed
$temp =& $array;

foreach($path as $key) {
$temp =& $temp[$key];
}
$temp = $value;
}

set($path, $arr);
//or
set($path, $arr, 'some value');

Unsetter

This will unset the final key in the path:

function unsetter($path, &$array) {
//$path = explode('.', $path); //if needed
$temp =& $array;

foreach($path as $key) {
if(!is_array($temp[$key])) {
unset($temp[$key]);
} else {
$temp =& $temp[$key];
}
}
}
unsetter($path, $arr);

*The original answer had some limited functions that I will leave in case they are of use to someone:

Setter

Make sure to define $array to be passed by reference &$array:

function set(&$array, $path, $value) {
//$path = explode('.', $path); //if needed
$temp =& $array;

foreach($path as $key) {
$temp =& $temp[$key];
}
$temp = $value;
}

set($arr, $path, 'some value');

Or if you want to return the updated array (because I'm bored):

function set($array, $path, $value) {
//$path = explode('.', $path); //if needed
$temp =& $array;

foreach($path as $key) {
$temp =& $temp[$key];
}
$temp = $value;

return $array;
}

$arr = set($arr, $path, 'some value');

Creator

If you wan't to create the array and optionally set the value:

function create($path, $value=null) {
//$path = explode('.', $path); //if needed
foreach(array_reverse($path) as $key) {
$value = array($key => $value);
}
return $value;
}

$arr = create($path);
//or
$arr = create($path, 'some value');

For Fun

Constructs and evaluates something like $array['b']['x']['z'] given a string b.x.z:

function get($array, $path) {
//$path = explode('.', $path); //if needed
$path = "['" . implode("']['", $path) . "']";
eval("\$result = \$array{$path};");

return $result;
}

Sets something like $array['b']['x']['z'] = 'some value';:

function set(&$array, $path, $value) {
//$path = explode('.', $path); //if needed
$path = "['" . implode("']['", $path) . "']";
eval("\$array{$path} = $value;");
}

Unsets something like $array['b']['x']['z']:

function unsetter(&$array, $path) {
//$path = explode('.', $path); //if needed
$path = "['" . implode("']['", $path) . "']";
eval("unset(\$array{$path});");
}

Split a string to form multidimensional array keys?

This ought to populate the sub-arrays for you if they haven't already been created and set keys accordingly (codepad here):

function set_opt(&$array_ptr, $key, $value) {

$keys = explode('.', $key);

// extract the last key
$last_key = array_pop($keys);

// walk/build the array to the specified key
while ($arr_key = array_shift($keys)) {
if (!array_key_exists($arr_key, $array_ptr)) {
$array_ptr[$arr_key] = array();
}
$array_ptr = &$array_ptr[$arr_key];
}

// set the final key
$array_ptr[$last_key] = $value;
}

Call it like so:

$opt_array = array();
$key = 'grandParent.parent.child';

set_opt($opt_array, $key, 'foobar');

print_r($opt_array);

In keeping with your edits, you'll probably want to adapt this to use an array within your class...but hopefully this provides a place to start!

Concatenate recursive key of an array php

Try this:

$arr1 = array("xxx"=>array(
"yyy" => array("text" => "test offline2"),
"yyy2" => array("text"=> "test offline")
),
"usual_name" => "test offline"
);

$arr2 = array();
foreach ($arr1 as $key1 => $value1) {
if(is_array($value1)) {
foreach ($value1 as $key2 => $value2) {
if(is_array($value2))
{
foreach ($value2 as $key3 => $value3) {
$arr2[$key1.'.'.$key2]= $value3;
}
}
}
}
else {
$arr2[$key1]= $value1;
}
}


Related Topics



Leave a reply



Submit