12

I'm trying to edit an array on the fly, inside a foreach loop. I basically analyse each key, and if this key match the one I want, I want to add another entry in the array immediately after this one.

If I take this code,

$values = array(
    'foo' => 10,
    'bar' => 20,
    'baz' => 30
);

foreach($values as $key => $value){
    print $value . ' ';
    if($key == 'bar'){
        $values['qux'] = 21;
    }
}

I've got 2 problems,

  • first, the output is 10 20 30 instead of the expected 10 20 30 21
  • second, even if I solve the first problem, my value will still be added at the end of my array

How could I add the qux entry between bar and baz ones?

Thanks for your ideas.

2
  • 1
    It's probably because you're not creating a new array, but use the old array to store the value in. That's why it's at the end of your array. To do what you want to do is to make a new variable let's say $aData and insert the values in there with your foreach loop. Commented Jan 29, 2015 at 14:24
  • 1
    You don't need a second array to achieve this. Instead of foreach use a for loop and iterate through the length of the array and using the index variable of the for loop, add whatever you want to your array. Commented Sep 6, 2016 at 18:26

4 Answers 4

20

Foreach will not loop through new values added to the array while inside the loop.

If you want to add the new value between two existing values, you could use a second array:

$values = array(
    'foo' => 10,
    'bar' => 20,
    'baz' => 30
);
$newValues = array();
foreach($values as $key => $value) 
{
    $newValues[$key] = $value;
    if($key == 'bar') 
    {
        $newValues['qux'] = 21;
    }
}
print implode(' ', $newValue);

Also, see one of my favorite questions on StackOverflow discussing the foreach loop: How does PHP 'foreach' actually work?

Sign up to request clarification or add additional context in comments.

5 Comments

@Dennis Then you should have posted it as an answer instead
Upvoted your comment ;) But it was not there when I started writing the answer.
I know @LarsEbert, i don't blame you haha. And meagar, yea could do that.. but Lars already did so.
Thanks. As I expected, it seems I'll need to loop twice on my array. One time to add the value, and one time to treat the array...
This was a much needed example to the process.
5

You can use the ampersand sign before the value.

//populate all the promos into their promoG groups
foreach($unclaimedPromoGroups as &$unclaimedPromoGroup) {
    $_promo = new Promo();
    $_promo->promoGroupID = $unclaimedPromoGroup['promo_groupID'];
    $promo = $_promo->getGroupPromos();
    $unclaimedPromoGroup["promos"] = $promo;
}

2 Comments

This is such a simple and elegant solution, very good!
This is such a simple and elegant solution that doesn't answer the OP question.
2

For this you need to create a new array,

<?php
$values = array(
    'foo' => 10,
    'bar' => 20,
    'baz' => 30
);

$newarray = array();
foreach($values as $k => $v) 
{
    $newarray[$k] = $v;
    if($k == 'bar') 
        $newarray['qux'] = 21;
}

echo implode(' ', $newarray);

Demo:
http://3v4l.org/N4XgB

1 Comment

This will not add the new value between bar and baz.
1

The solution below uses the same array.

$values = array(
    'foo' => 10,
    'bar' => 20,
    'baz' => 30
);

function match($niddle, $haystack, $push, $offset = 0) {
    foreach(array_slice($haystack, $offset) as $key => $value) 
    {
        print $value . ' ';
        if($key == $niddle) 
        {
            $i = array_search($niddle, array_keys($haystack)) + 1;
            $haystack = array_slice($haystack, 0, $i, true) + $push + array_slice($haystack, $i, count($haystack) - $i, true);
            $haystack = match($niddle, $haystack, $push, $i);
            break;
        }
    }

    return $haystack;
}

$values = match('bar', $values, array('qux'=>21));

var_dump($values);

2 Comments

It still does not print the new value in the same loop.
Sure, the new entry is added. But unfortunately the foreach loop wont access it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.