Remove dynamic array of keys from multidimensional array [duplicate] - php

This question already has answers here:
Unset inside array_walk_recursive not working
(3 answers)
Closed 2 years ago.
I've looked through articles and SO questions for the last hour and still can't find exactly what I'm looking for.
I have a single dimensional string array containing containing keys from my multidimensional array. Both arrays are dynamic. I need a way to remove every key in the 1D from the MD array.
It's hard to explain, so let me just show you.
$dynamicKeys = ['date', 'name', 'account'];
$arrayRequiringSanitization = [
'name' => [
'first' => 'Homer',
'last' => 'simpson'
],
'age' => 'unknown',
'facts' => [
'history' => [
'date' => 'whenever',
'occurred' => 'nope'
],
'is' => 'existing'
]
];
function removeDynamicValues($arr, $vals) {
// this is where i need help
}
The removeDynamicValues function should take the $arrayRequiringSanitization and $dynamicKeys and return an array that looks as follows:
$arrayRequiringSanitization = [
'age' => 'unknown',
'facts' => [
'history' => [
'occurred' => 'nope'
],
'is' => 'existing'
]
];
So basically, it removed the name sub array and the date sub sub property. The important part is that both arrays are dynamic, and it's not known how deep $arrayRequiringSanitization will be nested.
Let me know if I need to provide further clarrification.

You can do this quite easily with recursion. Here's the code.
/**
* #param array<mixed> $arr initial array
* #param array<string|int> $vals array of keys that need to be deleted
* #return array<mixed>
*/
function removeDynamicValues(array $arr, array $vals): array
{
$out = [];
foreach ($arr as $key => $value) {
if (!in_array($key, $vals, true)) {
$out[$key] = is_array($value) ? removeDynamicValues($value, $vals) : $value;
}
}
return $out;
}

Related

PHP - foreach loop not return all keys and values [duplicate]

This question already has answers here:
PHP Associative Array Duplicate Keys
(6 answers)
Closed 4 months ago.
I have an array in my php code
$list = array(
'RETAIL' => 'SUPERMARKET'
'RETAIL' => 'BAR'
'RETAIL' => 'DEP. MARKET'
'BUSINESS' => 'HOTEL'
'BUSINESS' => 'PUB'
'OTHER' => 'GROCERY'
'OTHER' => 'BUTCHERY'
// I have 20+ items
);
foreach( $list as $type => $name ){
var_dump($type,$name);
}
//var_dump() output
// RETAIL SUPERMARKET
// BUSINESS HOTEL
// OTHER BUTCHERY
I'm facing the problem that when I try to loop the array only three values will be returned and the rest are ignored. How I can fix this?
I'm trying to loop the array to save the data into a custom wordpress database. With the same way I've successfully looped another array inserted the keys and values into the db.
I think a better structure for your array would something like this
$list = [
'RETAIL' => [
'BAR',
'RESTAURANT'
]
];
And you could loop over like so
foreach ($list as $businessType => $businesses) {
foreach ($businesses as $business) {
echo "<li>{$business}</li>";
}
}
Just an example
As a general way of handling instances where you have more than one element to each piece of data (even when it's not in a tree structure like this may be), you should structure each item in the list as either an array or object, eg:
$list_of_arrays = [
['RETAIL', 'SUPERMARKET'],
['RETAIL', 'BAR'],
['RETAIL', 'DEP. MARKET'],
];
foreach( $list_of_arrays as $array ){
echo "<li>{$array[0]} {$array[1]}</li>";
}
or
$list_of_objects = [
(object)['type' => 'RETAIL', 'subtype' => 'SUPERMARKET'],
(object)['type' => 'RETAIL', 'subtype' => 'BAR'],
(object)['type' => 'RETAIL', 'subtype' => 'DEP. MARKET'],
];
foreach( $list_of_objects as $object ){
echo "<li>{$object->type} {$object->subtype}</li>";
}
Maybe I show heavily but as you only have two data for each entity, why your table is not built like this at the base...?
$list = array(
'SUPERMARKET'=>'RETAIL',
'BAR'=>'RETAIL',
'DEP. MARKET'=>'RETAIL',
'HOTEL'=>'BUSINESS',
'PUB'=>'BUSINESS',
'GROCERY'=>'OTHER',
'BUTCHERY'=>'OTHER'
// I have 20+ items
);
You do have keys that uniquely identify entities.

How to convert PHP arrays?

This is an array of PHP database output:
[
[hi]=>array(
[text] => 'ok'
)
[work]=>array(
[text] => 'usa'
)
[city]=>array(
[text] => 'newyork'
)
]
How do I convert it to look like this:
[
[hi]=> 'ok'
[work]=> 'usa'
[city]=> 'newyork'
]
You just want to loop over the array and build your newly formatted array.
<?php
$arr = [
'please' => [
'text' => 'it'
],
'use' => [
'text' => 'will'
],
'google' => [
'text' => 'help'
]
];
$formattedArr = [];
foreach ($arr as $k => $v) {
$formattedArr[$k] = $v['text'];
}
Another way using some array sorting methods to get us a one liner:
$formattedArr = array_combine( array_keys($arr), array_column($arr, 'text'));
array_combine is a php function that creates a new array using an array for keys and an array for values.
Simply enough, array_keys gets - you guessed it - the keys of the array.
array_column creates an array of a selected property from an inner array, so in this case, it goes plucks the 'text' values from the inner arrays.

Remove all elements of an associative array if they have the a specific word in the key [duplicate]

This question already has answers here:
Recursively remove empty elements and subarrays from a multi-dimensional array
(8 answers)
PHP Remove elements from associative array
(9 answers)
Remove Specific key value pair from PHP array
(3 answers)
Closed 5 years ago.
I would like to remove all elements of an associative array if the key has a substring of 'TB1' in the key.
My array looks like:
$output= [
'TB1_course' => 'required'
'TB1_session' => 'required'
'TB2_course' => 'required'
]
I would like to remove TB1_course and TB1_session, so that my final array looks like:
$output =[
'TB2_course' => 'required
]
Is there any way to go about doing this in an easy concise fashion?
My initial guess was to use a for each loop:
foreach ($output as $key =>$value){
//remove
}
Thank you for all the help!
Filter the array by key:
$input = [
'TB1_course' => 'required',
'TB1_session' => 'required',
'TB2_course' => 'required',
];
$filter = function ($key) {
return substr($key, 0, 4) === 'TB2_';
};
$output = array_filter($input, $filter, ARRAY_FILTER_USE_KEY);
var_dump($output);
Output:
array(1) {
'TB2_course' =>
string(8) "required"
}
See http://php.net/array_filter for the documentation of the array_filter function that is useful to filter arrays.

Transpose data in an associative array of indexed arrays [duplicate]

This question already has answers here:
Transposing multidimensional arrays in PHP
(12 answers)
Closed 6 months ago.
I'm not sure how to search for the problem I'm facing, so that's why I'm asking here.
I want to know if there is a native php-function to transform following array I get from a html-form:
Original Array
$array = [
'product_template_id' => [
'0' => '1',
'1' => '2'
],
'amount' => [
'0' => '50',
'1' => '100'
]
]
Desired Array
$array = [
'0' => [
'product_template_id' => '1',
'amount' => '50'
],
'1' => [
'product_template_id' => '2',
'amount' => '100'
]
]
I know this can be done with a loop, but that's not what I'm asking for.
PS(not my main question, just a sidequestion): How can I bulk format code in stackoverflow? Is it always 4 spaces? How can I perform the formatting quicker?
edit: PS is not the main question, it is more of a sidenote which has already been answered by #RiggsFolly
Just as prove of concept you can use array_map:
$keys = array_keys($array);
// For < PHPv5.6
// $zip = call_user_func_array('array_map', array_merge([null], $array));
$zip = array_map(null, ...array_values($array));
$result = array_map(function ($item) use ($keys) {
return array_combine($keys, $item);
}, $zip);
Here is working demo.
But in practice, there is too much overhead for so simple problem.
EDIT:
Here I am zipping (getting one corresponding element from each array and creating an array of this elements) all child arrays. It is done with array_map using its property:
An interesting use of this function is to construct an array of arrays, which can be easily performed by using NULL as the name of the callback function
As array_map can take an arbitrary number of arrays, I supply them to it with '...' splat operator.
This does what you need!
for ($x = 0; $x < count($array['amount']); $x ++) {
$arr[$x] = [
'product_template_id' => $array['product_template_id'][$x],
'amount' => $array['amount'][$x],
];
}
See here for a working example https://3v4l.org/dokHK

Get list of values inside a multi-dimensional php array [duplicate]

This question already has answers here:
Is there a function to extract a 'column' from an array in PHP?
(15 answers)
Closed 6 years ago.
I need to change this array:
$array = [
[0] => [
'id' => '100'
],
[1] => [
'id' => '200'
],
[2] => [
'id' => '300'
]
];
Into this:
$array2 = [100, 200, 300];
A long time ago I found a built-in PHP function which could do this for me. But i can't for the life of me remember which one it was. Of course I could do it manually, but it would be easier and more readable if I could use a builtin PHP function
Use array_column like this: array_column($array, 'id');
1st solution:
Use array_map() function with inline function:
$array2 = array_map(function($arrayElement){return $arrayElement['id'];}, $array);
2nd solution:
Use foreach loop:
function getValues($array, $index)
{
$result = array();
foreach($array as $element)
{
if(isset($element[$index])) //check if index exists
$result[] = $element[$index];
}
return $result;
}
$array2 = getValues($array, 'id');
This function has two parameters: array from which you gets values and index, for example 'id'.
Result of two methods is the same:
Array
(
[0] => 100
[1] => 200
[2] => 300
)

Categories