Related
There are two arrays:
$arrOne = [1, 3, 4];
$arrTwo = [2, 5,];
$newArr = [];
How to merge to get like this;
$newArr = [1, 2, 3, 4, 5];
Now displays through one, this option is not suitable.
foreach ($arrOne as $k => $v) {
$newArr[] = $v;
$newArr[] = $arrTwo[$k];
}
Here is another example. Tthe values can be different in the array.
$arrOne = [154, 32, 15];
$arrTwo = [682, 124,];
Again for this example it is necessary that the values from the second array always be at 2 and 5 positions in the new array:
$newArr = [154, 682, 32, 15, 124];
You can use array_splice to merge the arrays in the intended way to the specific indices:
array_splice( $arrOne, 1, 0, $arrTwo[0]);
array_splice( $arrOne, 4, 0, $arrTwo[1]);
var_dump($arrOne);
Demo 1:
Using original data:
$arrOne = [1, 3, 4];
$arrTwo = [2, 5,];
https://3v4l.org/dAMav
Demo 2:
Using second set of data:
$arrOne = [154, 32, 15];
$arrTwo = [682, 124,];
https://3v4l.org/Xhl3K
You can use array_merge and sort functions to achieve this as following:
$newArr = array_merge($arrOne, $arrTwo); // it will be [1, 3, 4, 2, 5]
sort($newArr); // it will sort array [1, 2, 3, 4, 5]
You can use $newArr now which have sorted data
$arrOne = [1, 3, 4];
$arrTwo = [2, 5];
$newArr = [];
foreach($arrOne as $key => $one) {
switch($key) {
case 1:
$newArr[] = $arrTwo[0];
break;
case 4:
$newArr[] = $arrTwo[1];
break;
}
$newArr[] = $one;
}
if(count($newArr) < 5) {
$newArr[] = $arrTwo[1];
}
Demo link
Here we are considering there will be always two elements in second array
$arrayOne = [12,23,45,56,65,78,99];
$arrayTwo = [2,5];
$mergedArray = [];
foreach($arrayOne as $key => $value) {
$position = $key + 1;
if ($position === 2) {
$mergedArray[] = $arrayTwo[0];
} else if ($position === 4) {
$mergedArray[] = $arrayTwo[1];
}
$mergedArray[] = $value;
}
I have values 1,2,3 and it will create another value like below and produce results by summing. As there are 3 values so that it will create three arrays. if it were 5 values then 5 such arrays are required.
1 2 3
1 2 3
1 2 3
Result is : 1 3 6 5 3
What I am doing is :
$a=[1,2,3];
$b=$a;
$c=$a;
$d=[];
array_push($a,0,0);
array_unshift($b,0);
array_push($b,0);
array_unshift($c,0,0);
$d = array_map(function () {
return array_sum(func_get_args());
}, $a,$b,$c);
print_r($d);
I am not able to find the way to do this for more values than 3 and dynamically. So that I have to just put the values and it gives me the result. I am not asking for the code but you can help me with that how I should approach it. Thanks.
I recommend a linear approach with no preparations or padding or data bloat.
Use the indexes and simple arithmetic to add values to their desired element in the output.
Code: (Demo)
$array = range(1, 3);
$result = [];
foreach ($array as $shifter => $unused) {
foreach ($array as $index => $value) {
$key = $shifter + $index;
$result[$key] = ($result[$key] ?? 0) + $value;
}
}
var_export($result);
// [1, 3, 6, 5, 3]
This is very clean, readable, maintainable, and most efficient.
While $shifter = 0, $key will be 0, 1 then 2; forming [1, 2, 3].
While $shifter = 1, $key will be 1, 2 then 3; forming [1, 3, 5, 3].
While $shifter = 2, $key will be 2, 3 then 4; forming [1, 3, 6, 5, 3].
If you're using PHP 7.4+ you can use the below...
// Ensure the keys are indexed not associative.
$input = array_values( [ 1, 2, 3, 4, 5 ] );
// Create rows.
$rows = [];
foreach ( $input as $key => $value ) {
$rows[ $key ] = array_merge( array_fill( 0, $key, 0 ), $input );
}
// Sum values.
$output = array_map( function() {
return array_sum( func_get_args() );
}, ...$rows );
If you're using a PHP version below 7.4 you can do...
// Ensure the keys are indexed not associative.
$input = array_values( [ 1, 2, 3 ] );
// Create rows.
$rows = [];
foreach ( $input as $key => $value ) {
$rows[ $key ] = array_merge( array_fill( 0, $key, 0 ), $input );
}
// Sum values.
$output = call_user_func_array( 'array_map', array_merge( [ function() {
return array_sum( func_get_args() );
} ], $rows ) );
I'm thinking using an offset makes sense, it's the same as your approach, except I'm adding a 0 using array_fill
$arr = [1,2,3];
$result = [];
$offset = 0;
for($i = 0; $i < count($arr); $i++) {
$result = array_map(function () {
return array_sum(func_get_args());
}, $result, array_merge(array_fill(0, $offset, 0), $arr));
$offset++;
}
var_dump($result);
The advantage of using this is that it uses very little memory even for a very large initial array.
$names = ['john','brian','john','steven','michael','paul','mark','paul','brian'];
$money = [2, 4, 3, 7, 5, 8, 20, -2, 4];
The indexes of $names and $money correspond to each other.
I need to find the most efficient way to add common $money to each $names and print only the even values.
For example, john appears two times, with 2 and 3 money. So johnhas 5 money.
Desired output:
mark: 20
brian: 8
paul: 6
I am thinking of looping through each array, but this is O(n^2) Is there an easier way?
Make associative array (hash) for result:
$names = ['john','brian','john','steven','michael','paul','mark','paul','brian'];
$money = [2, 4, 3, 7, 5, 8, 20, -2, 4];
$result = [];
for ($i = 0; $i < count($names); $i++) {
if (!isset($result[$names[$i]])) {
$result[$names[$i]] = 0;
}
$result[$names[$i]] += $money[$i];
}
arsort($result); // reverse (big first) sort by money
print_r($result);
just loop through names and use it keys for money array:
$names = ['john','brian','john','steven','michael','paul','mark','paul','brian'];
$money = [2, 4, 3, 7, 5, 8, 20, -2, 4];
$res = [];
foreach ($names as $key => $value) {
$res[$value] = isset($res[$value]) ? $res[$value] + $money[$key] : $money[$key];
}
var_dump($res);
You just have to loop through $names once and set name as key in a result- variable.
$names = ['john','brian','john','steven','michael','paul','mark','paul','brian'];
$money = [2, 4, 3, 7, 5, 8, 20, -2, 4];
$data = [];
foreach ($names as $key => $name) {
if (!isset($data[$name])) {
$data[$name] = 0;
}
$data[$name] += $money[$key];
}
print_r($data);
Maybe you'll need a check, if both arrays have the same size.
$names = ['john','brian','john','steven','michael','paul','mark','paul','brian'];
$money = [2, 4, 3, 7, 5, 8, 20, -2, 4];
$result = [];
foreach ($names as $index => $name) {
if (empty($result[$name]) {
$result[$name] = $money[$index];
} else {
$result[$name] += $money[$index];
}
}
print_r($result);
I want to merge every element of two arrays, BUT if a value is in both arrays, then only add the values from the array which has the biggest amount of that element. The result array does not need to be sorted in any special way, but I did it here for readability.
Sample input:
$array1 = [1, 4, 7, 3, 3, 3];
$array2 = [4, 0, 3, 4, 9, 9];
Desired result:
[0, 1, 3, 3, 3, 4, 4, 7, 9, 9]
//a2 a1 a1 a1 a1 a2 a2 a1 a2 a2
Note, this will be used on big arrays, with unknown integer values. Is there a good way to do this that doesn't require too much time/processing power?
Try this:
<?php
$array1 = [1, 4, 7, 3, 3, 3];
$array2 = [4, 0, 3, 4, 9, 9];
function min_merge($arr1, $arr2) {
$arr1 = array_count_values($arr1);
$arr2 = array_count_values($arr2);
foreach ($arr2 as $index => $arr)
if (!isset($arr1[$index]) || $arr > $arr1[$index])
$arr1[$index] = $arr;
foreach ($arr1 as $index => $arr)
for ($i = 0; $i < $arr; $i++)
$final[] = $index;
return $final;
}
print_r(min_merge($array1, $array2));
Output:
Array (
[0] => 1
[1] => 4
[2] => 4
[3] => 7
[4] => 3
[5] => 3
[6] => 3
[7] => 0
[8] => 9
[9] => 9
)
Unsorted, but it contains all the numbers from [0, 1, 3, 3, 3, 4, 4, 7, 9, 9].
$count[0] = array_count_values($arr1);
$count[1] = array_count_values($arr2);
$out = array();
array_map(function($e) use(&$out, $count){
$n1 = (isset($count[0][$e])) ? $count[0][$e] : 0;
$n2 = (isset($count[1][$e])) ? $count[1][$e] : 0;
$next = ($n2 > $n1) ? array_fill(0, $n2, $e) : array_fill(0, $n1, $e);
$out = array_merge($out, $next);
}, array_keys($count[0] + $count[1]));
print_r($out);
My modernized rewrite of #DaveChen's answer using PSR-12 coding standards and eliminating single-use declarations. This approach uses one loop to determine the greater count for numbers shared by both value-count arrays, then a second loop to populate the result array. (Demo)
$counts1 = array_count_values($array1);
foreach (array_count_values($array2) as $number => $count) {
if ($count > ($counts1[$number] ?? 0)) {
$counts1[$number] = $count;
}
}
$result = [];
foreach ($counts1 as $number => $count) {
array_push($result, ...array_fill(0, $count, $number));
}
var_export($result);
My modernized rewrite of #Expedito's answer which does not abuse the array_map() (when array_map()'s return value is not used, use array_walk() for functional style programming), uses a foreach() loop to eliminate variable scope issues, and generally implements D.R.Y. techniques. (Demo)
$counts1 = array_count_values($array1);
$counts2 = array_count_values($array2);
$result = [];
foreach ($counts1 + $counts2 as $num => $cnt) {
array_push(
$result,
...array_fill(
0,
max($counts1[$num] ?? 0, $counts2[$num] ?? 0),
$num
)
);
}
var_export($result);
And I wanted to add a new approach of my own, despite the fact that it may or may not perform better than the other two snippets. The script makes one pass over the first value count arrays to populate a temporary array which demands which numbers from the first array should be represented in the result array. Then it isolates value intersections from the first array, value differences from the second array, then merges them. (Demo)
$counts1 = array_count_values($array1);
$counts2 = array_count_values($array2);
$keepFrom1 = array_keys(
array_filter(
$counts1,
fn($count, $number) => ($counts2[$number] ?? 0) <= $count,
ARRAY_FILTER_USE_BOTH
)
);
var_export(
array_merge(
array_intersect($array1, $keepFrom1),
array_diff($array2, $keepFrom1)
)
);
probably not the most optimized but
<?php
$one=[1, 4, 7, 3, 3, 3];
$two=[4, 0, 3, 4, 9, 9];
sort($one);
sort($two);
foreach($one as $el)
{
$combined[]=$el;
if (array_search($el,$two))
{
unset($two[array_search($el,$two)]);
}
}
foreach($two as $el)
{
$combined[]=$el;
}
sort($combined);
print_r($combined);
?>
I have multiple arrays, that get generated when a for loop completes. Now I need to get the total of all these arrays together, but in order, for instance:
array1(2, 4, 6, 8, 10)
array2(2, 4, 6, 8, 10)
I need to add the 2's together, the 4's etc etc
Then put them into another array.
Some combination of array_combine and array_sum seems to be the solution but I can't figure it out.
Any help is greatly appreciated.
You could do this without any php function except count,
$limit = count($array1);
for ($i = 0; $i < $limit; $i++) {
$array_res[$i] = $array1[$i] + $array2[$i];
should work. This will combine your two arrays and add them in the same order. But be sure you used sort or ksort on both of your arrays before if you're not sure they are in the same order.
1st stlye
$a1 = array(
"a" => 2
,"b" => 0
,"c" => 5
);
$a2 = array(
"a" => 3
,"b" => 9
,"c" => 7
,"d" => 10
);
$a3 = array_merge($a1, $a2);
print_r($a3);
2nd style
$a3 = $a1;
foreach($a2 as $k=>$v) {
if(array_key_exists($k,$a3))
$a3[$k] + = $v;
else
$a3[$k] = $v;
}
You should use array_map():
$arr1 = array(2, 4, 6, 8, 10);
$arr2 = array(1, 2, 3, 4, 5);
$arr3 = array_map(
function($foo, $bar){
return $foo+$bar;
},
$arr1, $arr2
);
print_r($arr3); // outputs:
Array
(
[0] => 3
[1] => 6
[2] => 9
[3] => 12
[4] => 15
)
You can do something like this
$a = array(2, 4, 6, 8, 10);
$b = array(2, 4, 6, 8, 10);
$c = array_map("test", $a, $b);
function test($a, $b) {
return $a + $b;
}
print_r($c);
As far as I understand your question You want sum of all the similar digits in both the array:
<?php
$array1= array(2, 4, 6, 8, 10);
$array2=array(2, 4, 6, 8, 10);
$array_sum=array();
foreach($array1 as $key1=>$val1)
{
$sum=0;
foreach($array2 as $key2 => $val2)
{
if($val1==$val2)
{
$sum=$sum+$val1;
}
}
$array_sum[]=$sum;
}
print_r($array_sum);
?>