Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the reason for this strange PHP behaviour?

Tags:

arrays

types

php

I have the following code:

$data = array(); // prep array
$data['aardvark'] = true;

print_r($data); // output array
echo "\n";
var_dump(in_array('zebra', $data));

The output is as follows:

Array
(
    [aardvark] => 1
)

bool(true)

Despite the fact that zebra is clearly not in the array. It looks like it's to do with PHP's loose type system. (bool) 'zebra' is true, and there's a true in the array so the in_array returns true?

I think I can see the logic, but it's flawed. Is this a PHP bug?

Cheers.

like image 912
Matthew Avatar asked Nov 23 '11 17:11

Matthew


4 Answers

Not a bug. You have it exactly right. To correctly find what you are looking for, you will have to do this:

if (in_array('zebra', $data, true)) {

Although this would probably be rare that you store different data types in the same array (strings and booleans). If you are storing data that are not a list, you should most likely be using an object instead.

like image 189
dqhendricks Avatar answered Nov 03 '22 19:11

dqhendricks


You are right. in_array()

bool in_array ( mixed $needle , array $haystack [, bool $strict = FALSE ] )

You must set the third parameter to true, if you want in_array() to test against the type too. Otherwise it will make loose comparison

var_dump(in_array('zebra', $data, true));

Usually this is no problem, because (in a clean design) usually all values are of the same type you know before you call in_array() and thus you can avoid calling it with mismatching types.

like image 44
KingCrunch Avatar answered Nov 03 '22 19:11

KingCrunch


This happens because the string 'zebra' is non-empty and a non-empty string other than '0' is interpreted by PHP as true and since there is a matching value in your array you get true as result.

PHP did a conversion from string to boolean. To avoid this conversion you need to pass a third argument as true to in_array:

var_dump(in_array('zebra', $data, true));
like image 34
codaddict Avatar answered Nov 03 '22 21:11

codaddict


"It's not a bug, it's a feature!" =)

Try doing in_array("zebra", $data, true); which will force "strict" checking (i.e. it will do a type-check on your variables).

like image 20
WWW Avatar answered Nov 03 '22 20:11

WWW