<?php
// we wanted the output of only selected array_keys from a big array from a csv-table
// with different order of keys, with optional suppressing of empty or unused values
$values = array
(
'Article'=>'24497',
'Type'=>'LED',
'Socket'=>'E27',
'Dimmable'=>'',
'Wattage'=>'10W'
);
$keys = array_fill_keys(array('Article','Wattage','Dimmable','Type','Foobar'), ''); // wanted array with empty value
$allkeys = array_replace($keys, array_intersect_key($values, $keys)); // replace only the wanted keys
$notempty = array_filter($allkeys, 'strlen'); // strlen used as the callback-function with 0==false
print '<pre>';
print_r($allkeys);
print_r($notempty);
/*
Array
(
[Article] => 24497
[Wattage] => 10W
[Dimmable] =>
[Type] => LED
[Foobar] =>
)
Array
(
[Article] => 24497
[Wattage] => 10W
[Type] => LED
)
*/
?>
array_replace
(PHP 5 >= 5.3.0)
array_replace — Reemplaza los elementos de los arrays pasados en el primer array
Descripción
$array
, array $array1
[, array $...
] )
array_replace() reemplaza los valores del primer
array con los mismos valores de todos los siguientes
arrays. Si la clave del primer array existe en el segundo array, su valor
será reemplazado por el valor del segundo array. Si la clave existe en el
segundo array y no en el primero, será creado en el primer array.
Si la clave sólo existe en el primer array, se dejará como está.
Si varios array son pasados para ser reemplazados, se procederá
en orden, los arrays posteriores sobreescribirán los valores anteriores.
array_replace() no es recursivo: reemplazará valores en el primer array por el tipo que sea en el segundo array.
Parámetros
-
array -
El array cuyos elementos son reemplazados.
-
array1 -
El array del cual se extraerán los elementos.
-
... -
Más arrays de los que se extraerán los elementos. Valores de arrays posteriores sobrescriben los valores anteriores.
Valores devueltos
Devuelve un array, o NULL en caso de error.
Ejemplos
Ejemplo #1 Ejemplo de array_replace()
<?php
$base = array("naranja", "plátano", "manzana", "frambuesa");
$reemplazos = array(0 => "piña", 4 => "cereza");
$reemplazos2 = array(0 => "uva");
$cesta = array_replace($base, $reemplazos, $reemplazos2);
print_r($cesta);
?>
El resultado del ejemplo sería:
Array
(
[0] => uva
[1] => plátano
[2] => manzana
[3] => frambuesa
[4] => cereza
)
Ver también
- array_replace_recursive() - Reemplaza los elementos de los arrays pasados al primer array de forma recursiva
I got hit with a noob mistake. :)
When the function was called more than once, it threw a function redeclare error of course. The enviroment I was coding in never called it more than once but I caught it in testing and here is the fully working revision. A simple logical step was all that was needed.
With PHP 5.3 still unstable for Debian Lenny at this time and not knowing if array_replace would work with multi-dimensional arrays, I wrote my own. Since this site has helped me so much, I felt the need to return the favor. :)
<?php
// Polecat's Multi-dimensional array_replace function
// Will take all data in second array and apply to first array leaving any non-corresponding values untouched and intact
function polecat_array_replace( array &$array1, array &$array2 ) {
// This sub function is the iterator that will loop back on itself ad infinitum till it runs out of array dimensions
if(!function_exists('tier_parse')){
function tier_parse(array &$t_array1, array&$t_array2) {
foreach ($t_array2 as $k2 => $v2) {
if (is_array($t_array2[$k2])) {
tier_parse($t_array1[$k2], $t_array2[$k2]);
} else {
$t_array1[$k2] = $t_array2[$k2];
}
}
return $t_array1;
}
}
foreach ($array2 as $key => $val) {
if (is_array($array2[$key])) {
tier_parse($array1[$key], $array2[$key]);
} else {
$array1[$key] = $array2[$key];
}
}
return $array1;
}
?>
[I would also like to note] that if you want to add a single dimensional array to a multi, all you must do is pass the matching internal array key from the multi as the initial argument as such:
<?php
$array1 = array( "berries" => array( "strawberry" => array( "color" => "red", "food" => "desserts"), "dewberry" = array( "color" => "dark violet", "food" => "pies"), );
$array2 = array( "food" => "wine");
$array1["berries"]["dewberry"] = polecat_array_replace($array1["berries"]["dewberry"], $array2);
?>
This is will replace the value for "food" for "dewberry" with "wine".
The function will also do the reverse and add a multi to a single dimensional array or even a 2 tier array to a 5 tier as long as the heirarchy tree is identical.
I hope this helps atleast one person for all that I've gained from this site.
To get exactly same result like in PHP 5.3, the foreach loop in your code should look like:
<?php
...
$count = func_num_args();
for ($i = 1; $i < $count; $i++) {
...
}
...
?>
Check on this code:
<?php
$base = array('id' => NULL, 'login' => NULL, 'credit' => NULL);
$arr1 = array('id' => 2, 'login' => NULL, 'credit' => 5);
$arr2 = array('id' => NULL, 'login' => 'john.doe', 'credit' => 100);
$result = array_replace($base, $arr1, $arr2);
/*
correct output:
array(3) {
"id" => NULL
"login" => string(8) "john.doe"
"credit" => int(100)
}
your output:
array(3) {
"id" => int(2)
"login" => NULL
"credit" => int(5)
}
*/
?>
Function array_replace "replaces elements from passed arrays into the first array" -- this means replace from top-right to first, then from top-right - 1 to first, etc, etc...
Instead of calling this function, it's often faster and simpler to do this instead:
<?php
$array_replaced = $array2 + $array1;
?>
If you need references to stay intact:
<?php
$array2 += $array1;
?>
In some cases you might have a structured array from the database and one
of its nodes goes like this;
<?php
# a random node structure
$arr = array(
'name' => 'some name',
'key2' => 'value2',
'title' => 'some title',
'key4' => 4,
'json' => '[1,0,1,1,0]'
);
# capture these keys values into given order
$keys = array( 'name', 'json', 'title' );
?>
Now consider that you want to capture $arr values from $keys.
Assuming that you have a limitation to display the content into given keys
order, i.e. use it with a vsprintf, you could use the following
<?php
# string to transform
$string = "<p>name: %s, json: %s, title: %s</p>";
# flip keys once, we will use this twice
$keys = array_flip( $keys );
# get values from $arr
$test = array_intersect_key( $arr, $keys );
# still not good enough
echo vsprintf( $string, $test );
// output --> name: some name, json: some title, title: [1,0,1,1,0]
# usage of array_replace to get exact order and save the day
$test = array_replace( $keys, $test );
# exact output
echo vsprintf( $string, $test );
// output --> name: some name, json: [1,0,1,1,0], title: some title
?>
I hope that this will save someone's time.
Function that replace empty vals with $replace = "N/A"
Function parametters :
$array as array => array to be parsed
$replace as string => replace
<?php
function rep_empty_vals_arr($array,$replace = "N/A")
{
$returned_array = array();
foreach($array as $k=>$v)
{
if(is_array($v))
{
$returned_array[$k] = rep_empty_vals_arr($v,$replace);
}
if(empty($v))
{
$returned_array[$k] = $replace;
}else{
$returned_array[$k] = $v;
}
}
return $returned_array;
}
?>
I would like to add to my previous note about my polecat_array_replace function that if you want to add a single dimensional array to a multi, all you must do is pass the matching internal array key from the multi as the initial argument as such:
$array1 = array( "berries" => array( "strawberry" => array( "color" => "red", "food" => "desserts"), "dewberry" = array( "color" => "dark violet", "food" => "pies"), );
$array2 = array( "food" => "wine");
$array1["berries"]["dewberry"] = polecat_array_replace($array1["berries"]["dewberry"], $array2);
This is will replace the value for "food" for "dewberry" with "wine".
The function will also do the reverse and add a multi to a single dimensional array or even a 2 tier array to a 5 tier as long as the heirarchy tree is identical.
I hope this helps atleast one person for all that I've gained from this site.
a little enhancement to dyer85 at gmail dot com's function below:
<?php
if (!function_exists('array_replace'))
{
function array_replace( array &$array, array &$array1, $filterEmpty=false )
{
$args = func_get_args();
$count = func_num_args()-1;
for ($i = 0; $i < $count; ++$i) {
if (is_array($args[$i])) {
foreach ($args[$i] as $key => $val) {
if ($filterEmpty && empty($val)) continue;
$array[$key] = $val;
}
}
else {
trigger_error(
__FUNCTION__ . '(): Argument #' . ($i+1) . ' is not an array',
E_USER_WARNING
);
return NULL;
}
}
return $array;
}
}
?>
this will allow you to "tetris-like" merge arrays:
<?php
$a= array(
0 => "foo",
1 => "",
2 => "baz"
);
$b= array(
0 => "",
1 => "bar",
2 => ""
);
print_r(array_replace($a,$b, true));
?>
results in:
Array
(
[0] => foo
[1] => bar
[2] => baz
)
Yep, thinking about it replacing from back to front, this works a trick!
here's a quick repalcement for PHP <=5.3
<?php
if (!function_exists('array_replace')){ function array_replace(){
$array=array();
$n=func_num_args();
while ($n-- >0) {
$array+=func_get_arg($n);
}
return $array;
}}
?>
For a backward compatible alternative, you might try something like this:
<?php
if (!function_exists('array_replace'))
{
function array_replace( array &$array, array &$array1 )
{
$args = func_get_args();
$count = func_num_args();
for ($i = 0; $i < $count; ++$i) {
if (is_array($args[$i])) {
foreach ($args[$i] as $key => $val) {
$array[$key] = $val;
}
}
else {
trigger_error(
__FUNCTION__ . '(): Argument #' . ($i+1) . ' is not an array',
E_USER_WARNING
);
return NULL;
}
}
return $array;
}
}
?>
