简体   繁体   English

range()和in_array()行为,我在这里做错了什么?

[英]range() and in_array() behaviour, what am I doing wrong here?

This is the code , check output here -> http://codepad.org/7n7dM54e 这是代码,检查输出 - > http://codepad.org/7n7dM54e

<?php

$key = "a";
$array = range("0","7");
echo "array is : \n";
var_dump($array);
echo "key is : $key \n";
echo "in_array result \n";
var_dump(in_array($key,$array)); // why is it true, 'a' is not a "0" string or 0 int
echo "array_search result \n";
var_dump(array_search($key,$array)); // why is it index 0

?>

Solution

in_array() and array_search() support a type-safe check with the third parameter set to true . in_array()array_search()支持类型安全检查,第三个参数设置为true No conversion will be performed and the values will be compared as is, with type taken into account (like with the === operator). 不会执行任何转换,并且将按原样比较值,并考虑类型(与===运算符一样)。

So if you pass true at the end of each function call, you'll get the expected results: 因此,如果您在每个函数调用结束时传递true ,您将获得预期的结果:

// Both should return false
var_dump(in_array($key, $array, true));
var_dump(array_search($key, $array, true));

Why this is happening 为什么会这样

Yep, it's definitely a type conversion, but not one that is specially implemented by in_array() or array_search() . 是的,它绝对是一种类型转换,但不是由in_array()array_search()专门实现的转换。 It's nothing more than the loose comparison performed by the == operator. 它只不过是==运算符执行的松散比较。

Both methods call a C function called php_search_array() . 两个方法都调用一个名为php_search_array()的C函数。 This function is defined in /ext/standard/array.c . 该函数在/ext/standard/array.c定义。 Here are some of the first few lines: 以下是前几行中的一些内容:

static void php_search_array(INTERNAL_FUNCTION_PARAMETERS, int behavior) /* {{{ */
{
    // ---------- snip ----------

    int (*is_equal_func)(zval *, zval *, zval * TSRMLS_DC) = is_equal_function;

    // ...

    if (strict) {
        is_equal_func = is_identical_function;
    }

    // ---------- snip ----------
}

If I'm not wrong, the is_equal_function you see there simply corresponds to (but may not actually be) the == operator, which does a very simple comparison regardless of data type. 如果我没有错,你看到的is_equal_function只对应于(但实际上可能不是) ==运算符,无论数据类型如何,都会进行非常简单的比较。 Type conversion may occur. 可能会发生类型转换。 (Likewise, is_identical_function corresponds to === .) (同样, is_identical_function对应于=== 。)

For example, '2abc' == 2 is true, but '2abc' == 3 is false. 例如, '2abc' == 2为真,但'2abc' == 3为假。 This is because comparing a string and an integer causes the string to be cast to integer before comparing. 这是因为比较字符串和整数会导致在比较之前将字符串强制转换为整数。 So casting the string '2abc' to an int returns 2. 因此,将字符串'2abc'强制转换为int将返回2。

So, like I said below, the same thing applies when you pass 'a' to both functions: it's being converted to an integer, resulting in 0 , which exists in the array returned by range() . 因此,就像我在下面所说的那样,当你将'a'传递给两个函数时同样适用:它被转换为一个整数,结果为0 ,它存在于range()返回的数组中。 And like I said, range() returns an array of integers (or floats) whether you pass integers or numeric strings as arguments. 就像我说的那样,无论是将整数还是数字字符串作为参数传递, range()返回一个整数(或浮点数)数组。

From the manual entry on PHP's comparison operators : PHP的比较运算符手动输入

If you compare a number with a string or the comparison involves numerical strings, then each string is converted to a number and the comparison performed numerically. 如果将数字与字符串进行比较或比较涉及数字字符串,则每个字符串将转换为数字,并且数字执行比较。


Old "Why is this happening" 旧“为什么会这样”

I think the internal implementations of in_array() and array_search() by default try to convert the needle to be of the same type of the elements in the array being searched. 我认为in_array()array_search()的内部实现默认尝试将针转换为与被搜索数组中元素相同的类型。 If that is the case, since range() returns an array of integers, the string 'a' is converted to an integer, which is 0 and would thus return results for both function calls. 如果是这种情况,由于range()返回一个整数数组,字符串'a'将转换为一个整数,该整数为0 ,因此将返回两个函数调用的结果。 Note that range() will produce an array of integers or floats even if you pass numbers as strings. 请注意,即使将数字作为字符串传递, range()也会生成整数或浮点数组。

Well , this seems to be a bug with arrays that have a '0' in it 好吧,这似乎是一个错误的数组,其中有一个'0'

If you change $array = range("0","7"); 如果你改变$array = range("0","7"); to $array = range("1","7"); to $array = range("1","7"); , you'll understand what I am trying to say ,你会理解我想说的

http://codepad.org/3099zpch http://codepad.org/3099zpch

Also read the comment's in the php manual http://php.net/manual/en/function.in-array.php 另请阅读php手册http://php.net/manual/en/function.in-array.php中的注释

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM