Unusual string collision in PHP [duplicate] - php

This question already has answers here:
PHP in_array() / array_search() odd behaviour
(2 answers)
Closed 4 months ago.
I have an array of lower case hex strings. For some reason, in_array is finding matches where none exist:
$x = '000e286592';
$y = '0e06452425';
$testarray = [];
$testarray[] = $x;
if (in_array($y, $testarray)) {
echo "Array element ".$y." already exists in text array ";
}
print_r($testarray);exit();
The in_array comes back as true, as if '0e06452425' is already in the array. Which it is not. Why does this happen and how do I stop it from happening?

Odd. This has something to do with the way that PHP compares the values in "non-strict" mode; passing the third argument (strict) as true no longer results in a false positive:
if (in_array($y, $testarray, true)) {
echo "Array element ".$y." already exists in text array ";
}
I'm still trying to figure out why, technically speaking, this doesn't work without strict checking enabled.

You can pass a boolean as third parameter to in_array() to enable PHP strict comparison instead of the default loose comparison.
Try this code
$x = '000e286592';
$y = '0e06452425';
$testarray = [];
$testarray[] = $x;
if (in_array($y, $testarray, true)) {
echo "Array element ".$y." already exists in text array ";
}
print_r($testarray);exit();

Related

array_search() returns 1 if $needle is 0 [duplicate]

This question already has answers here:
Is this php behaviour explained somewhere in manual? (strings with zeroes comparison)
(5 answers)
Closed 6 years ago.
This is weird thing I found with array_search();
$test = array(
1 => 'first',
2 => 'second'
);
Now if the needle to be searched comes as 0 For eg:
$val = 0;
$key = array_search($val, $test);
Now $key is returned as 1 (the first key).
Does anyone know how to deal with such behaviour and return false for this check ? Is it documented anywhere ? I've searched but not found even on SO.
Thanks!
This is not a bug, but how PHP handles comparisons. As $val is an integer, PHP will convert your strings to integers for the comparison. Converting 'first' to an integer will give you 0, and so the comparison is 0 == 0, which is obviously true. That's why it returns the first result.

What is wrong with the PHP function in_array(...)? [duplicate]

This question already has answers here:
PHP in_array() / array_search() odd behaviour
(2 answers)
Closed 6 years ago.
The PHP function in_array(...) "checks if a value exists in an array".
But I'm observing a very strange behavior on handling strings (PHP v7.0.3). This code
$needle = 'a';
$haystacks = [['a'], ['b'], [123], [0]];
foreach ($haystacks as $haystack) {
$needleIsInHaystack = in_array($needle, $haystack);
var_dump($needleIsInHaystack);
}
generates following output:
bool(true)
bool(false)
bool(false)
bool(true) <- WHAT?
The function returns true for every string $needle, if the $haystack contains an element with the value 0!
Is it really by design? Or is it a bug and should be reported?
If you do not set the third parameter of in_array to true, comparison is done using type coercion.
If the third parameter strict is set to TRUE then the in_array() function will also check the types of the needle in the haystack.
Under loose comparison rules, effectively 'a' is equal to 0 since (int)'a' == 0.

in_array() does not work [duplicate]

This question already has answers here:
PHP in_array() / array_search() odd behaviour
(2 answers)
Closed 6 years ago.
Why does this return true.
$needle = TRUE;
$haystack = array('that', 'this');
print in_array($needle, $haystack); // 1
EDIT: I am aware that one can pass in_array() the strict parameter to check types. I want to know why specifically the behaviour I show is exhibited.
Any non-empty string in PHP is equal to TRUE when loose comparison is made (i.e. type is ignored). You may test this by doing:
var_dump('this' == TRUE);
var_dump('that' == TRUE);
DEMO
But the results are quite different when strict comparison is made (i.e. type is taken into consideration):
var_dump('this' === TRUE);
var_dump('that' === TRUE);
DEMO
In order to enforce strict comparison in the function in_array, you have to set the optional third parameter to TRUE:
$needle = TRUE;
$haystack = array('that', 'this');
var_dump(in_array($needle, $haystack, TRUE));
DEMO

Strange PHP array behaviour [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
PHP String in Array Only Returns First Character
I've got following problem. When I run script below I got string(1) "F" as an output. How is that possible? No error, notice displayed.. nothing. Key whatever doesn't exist in $c. Can you explain that?
<?php
$c = 'FEEDBACK_REGISTER_ACTIVATION_COMPLETED_MSG';
var_dump ($c['whatever']);
?>
I'm having this issue on PHP 5.3.3. (LINUX)
PHP lets you index on strings:
$str = "Hello, world!";
echo $str[0]; // H
echo $str[3]; // l
PHP also converts strings to integers implicitly, but when it fails, uses zero:
$str = "1";
echo $str + 1; // 2
$str = "invalid";
echo $str + 1; // 1
So what it's trying to do is index on the string, but the index is not an integer, so it tries to convert the string to an integer, yielding zero, and then it's accessing the first character of the string, which happens to be F.
Through Magic type casting of PHP when an associative array can not find the index, index itself is converted to int 0 and hence it is like
if
$sample = 'Sample';
$sample['anystring'] = $sample[0];
so if o/p is 'S';

PHP Search Array Question

I need to have an array_search search my array strictly making sure that the item is identical (meaning the whole thing is the same thing as the input value). I know about the third variable in a array_search() function in PHP - the Strict one, but I don't want it to check if its the same instance, as it is not. How would I do this?
Here is the code I'm currently using:
array_search(some, array(someItem,anothervariable, yetanothervariable, some));
//output - 0 (the first item) which contains some but isn't exactly some.
Requested output:
Instead of outputting the first item that contains some, someItem, it would output the key for the last item, 3, that is the exact search value.
Array search with strict is equivalent to the === operator.
Array search without strict is equivalent to the == operator.
If you need some sort of special comparison that isn't covered by either of them (comparing elements of objects for example) then you need to write a loop.
Are you open to using a foreach loop instead of array_search?
If so try this:
$haystack = array('something', 'someone', 'somewhere', 'some');
$needle = 'some';
foreach($haystack as $key=>$straw){
if($straw === $needle){
$straws[$key] = $straw;
}
}
print_r($straws);
it will print
Array ( [3] => some )
Or you could use array_keys() with the search value specified.
Then, using the same $haystack and $needle above:
$result = array_keys($haystack,$needle,TRUE);
print_r($result);
This returns:
Array ( [0] => 3 )
The first argument is the array to return keys from, The second arg is the search value, if you include this arg, then only keys from array elements that match the search value are returned. Including the third boolean arg tells the function to use match type as well (===).
Not really sure what you are asking but in PHP strict comparison is achieved with the
triple equal sign (===). This means that both the value and the type must be the same.
So if you compare a string "1" and an integer 1 with === it will fail.
If strict is false then comparing string "1" with integer 1 would succeed.
This is the meaning of strict in the array_search case.
I implemented array_search below so you can see what it is doing.
function my_array_search($input, $search_array, $strict=false) {
if(is_array($search_array)) {
foreach($search_array as $key => $val) {
if($strict === true) {
if($val === $input) {
return $key;
}
} else {
if($val == $input) {
return $key;
}
}
}
}
}

Categories