5
$posts = array( "message" => 'this is a test message' ); foreach ($posts as $post) { echo $post['message']; } 

Why does the above code only output the first letter in message? "t".

2
  • I'm actually surprised it prints anything at all... You shouldn't be able to index into a string using an associative parameter (ie. a string)... I'd say this probably undefined behaviour at best. Commented Jul 21, 2009 at 8:21
  • 1
    @Matthew: The explanation for that is in my answer. Commented Jul 21, 2009 at 8:23

3 Answers 3

12

foreach takes each element of the array and assigns it to the variable. To get the results I assume you are expecting you just need to do:

foreach ($posts as $post) { echo $post; } 

The specifics as to why your code didn't work: $post would be the contents of the array element - in this case a string. Because PHP isn't strongly typed / supports type juggling, you can in fact work with a string as if it were an array, and get to each character in the sequence:

foreach ($posts as $post) { echo $post[0]; //'t' echo $post[1]; //'h' } 

Obviously $post['message'] therefore is not a valid element, and there is no explicit conversion from (string)'message' to int, so this evals to $post[0].

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

2 Comments

((int) 'message') is pretty well defined: de.php.net/manual/en/…
Very true: bad choice of vocabulary on my part to express what I meant
6
# $posts is an array with one index ('message') $posts = array( "message" => 'this is a test message' ); # You iterate over the $posts array, so $post contains # the string 'this is a test message' foreach ($posts as $post) { # You try to access an index in the string. # Background info #1: # You can access each character in a string using brackets, just # like with arrays, so $post[0] === 't', $post[1] === 'e', etc. # Background info #2: # You need a numeric index when accessing the characters of a string. # Background info #3: # If PHP expects an integer, but finds a string, it tries to convert # it. Unfortunately, string conversion in PHP is very strange. # A string that does not start with a number is converted to 0, i.e. # ((int) '23 monkeys') === 23, ((int) 'asd') === 0, # ((int) 'strike force 1') === 0 # This means, you are accessing the character at position ((int) 'message'), # which is the first character in the string echo $post['message']; } 

What you possibly want is either this:

$posts = array( array( "message" => 'this is a test message' ) ); foreach ($posts as $post) { echo $post['message']; } 

Or this:

$posts = array( "message" => 'this is a test message' ); foreach ($posts as $key => $post) { # $key === 'message' echo $post; } 

2 Comments

That's not really solving the problem, which is an obvious mis-conception about how foreach works with arrays.
'Solving the problem'? Of course I can't solve the problem without knowing what he wants to achieve with his script, I can only answer his question and give working examples. But I do think the info here is enough to make his script work.
4

I'd add to iAn's answer something: if you want somehow to access to the key of the value, use this:

foreach ($posts as $key => $post) { echo $key . '=' . $post; } 

Result:

message=this is a test message 

Comments