Reputation: 2768
I'm looking for a way to replace nested foreach loops with a functional programming approach. Here is the sample data:
$mode[1] = [1, 2, 5, 6];
$mode[0] = [3, 4, 7, 8];
Currently my code is this:
foreach ($mode as $key => $value):
foreach ($value as $v):
$modes[$v] = $key;
endforeach;
endforeach;
echo '<pre>' . print_r($modes, 1) . '</pre>';
This generates the desired output (which can be thought of as flipping a 2d array):
array (
1 => 1,
2 => 1,
5 => 1,
6 => 1,
3 => 0,
4 => 0,
7 => 0,
8 => 0,
)
Does anyone know how the foreach code block can be replaced with a functional programming alternative?
Upvotes: 0
Views: 1399
Reputation: 47991
I think array_walk()
partnered with a Union Operator and array_fill_keys()
seems like a clean choice for this task:
Code: (Demo)
$mode[1] = [1, 2, 5, 6];
$mode[0] = [3, 4, 7, 8];
$result = []; // declare empty array so that union operator works
array_walk($mode, function($a, $k) use (&$result) { $result += array_fill_keys($a, $k); });
var_export($result);
To avoid declaring any variables in the global scope, call array_reduce()
on the first level keys and use those keys to access the second level subarray. (Demo)
var_export(
array_reduce(
array_keys($mode),
fn($result, $k) => $result += array_fill_keys($mode[$k], $k),
[]
)
);
Output (from either snippet):
array (
1 => 1,
2 => 1,
5 => 1,
6 => 1,
3 => 0,
4 => 0,
7 => 0,
8 => 0,
)
Upvotes: 1
Reputation: 781917
You can do it with array_map()
array_map(function($key, $value) use (&$modes) {
array_map(function($v) use (&$modes) {
$modes[$v] = $key;
}, $value);
}, array_keys($mode), array_values($mode));
I'm not sure why you would want to do this, the foreach
version seems much clearer to me.
Upvotes: 2
Reputation: 1293
I'd use array_fill_keys to create the mode arrays, then merge them into one:
$modes = array_fill_keys($mode[1], 1) + array_fill_keys($mode[0], 0);
For legibility, you can split it up into multiple lines, but this should get you an idea.
Bonus: you can abstract this code even more, if you don't know the contents of $mode
exactly:
$modes = [];
foreach ($mode as $key => $value) {
$modes += array_fill_keys($value, $key);
}
Upvotes: 0
Reputation: 192
use array_flip for exchange key and val together in array :
but because of you want use multidimensional array you should have a loop :
<?php
$mode[0] = array(1, 2, 5, 6);
$mode[1] = array(3, 4, 7, 8);
for($i=0;$i<2;$i++)
{
$flipped = array_flip($mode[$i]);
print_r($flipped);
}
?>
output:
Array
(
[1] => 0
[2] => 1
[5] => 2
[6] => 3
)
Array
(
[3] => 0
[4] => 1
[7] => 2
[8] => 3
)
Upvotes: -4