如何在PHP中检查一个整数是否在一定范围内?

105

如何检查给定的数字是否在一定范围内?


16个回答

177

表达式:

($min <= $value) && ($value <= $max)

如果$value$min$max之间(包括边界),则返回true

有关比较运算符的更多信息,请参见PHP文档


1
不会的。两个比较运算符都应该是<=,或者表达式的第二部分的操作数应该交换。($value 不应该大于 $max)。 - GolezTrol
1
你一定是在我纠正错误的时候添加了那个评论... 这个表达现在是正确的。 - Dancrumb
3
根据OP要求的“integer”是否真的意味着整数,当$value为浮点数时,这将产生错误结果。另外,由于比较是宽松的,传递字符串可能会产生错误的结果,例如(0 <= 'string') && ('string' <= 10) );会因为类型转换而返回true - Gordon
PHP中没有提供一个函数来检查一个数字是否在两个数之间。 - Ebrahim Bashirpour
我建议放弃使用圆括号,而是使用“and”代替“&&”,因为“and”的优先级要低得多(以防代码以后发生大量变化)。 - Mikko Rantalainen
显示剩余4条评论

134

53

25
值得注意的是,由于生成范围而产生了一定的内存开销。 - Dancrumb
6
但是,当范围很大时,这种解决方案非常缓慢且需要大量内存。 - hanshenrik
同意,这种方法比被接受的解决方案不够优雅,并且在更大的数组上执行起来需要更长时间,因为你必须在数组中执行搜索以找到值。使用被接受的解决方案更快、占用更少的内存,并且代码行数也一样少。 - dmcoding
不处理浮点数值。 - Richard Muvirimi

23
你可以编写一个小的辅助函数来完成这个任务:
/**
 * Determines if $number is between $min and $max
 *
 * @param  integer  $number     The number to test
 * @param  integer  $min        The minimum value in the range
 * @param  integer  $max        The maximum value in the range
 * @param  boolean  $inclusive  Whether the range should be inclusive or not
 * @return boolean              Whether the number was in the range
 */
function in_range($number, $min, $max, $inclusive = FALSE)
{
    if (is_int($number) && is_int($min) && is_int($max))
    {
        return $inclusive
            ? ($number >= $min && $number <= $max)
            : ($number > $min && $number < $max) ;
    }

    return FALSE;
}

并且您可以像这样使用它:

var_dump(in_range(5, 0, 10));        // TRUE
var_dump(in_range(1, 0, 1));         // FALSE
var_dump(in_range(1, 0, 1, TRUE));   // TRUE
var_dump(in_range(11, 0, 10, TRUE)); // FALSE

// etc...

12
if (($num >= $lower_boundary) && ($num <= $upper_boundary)) {

如果您不希望边界值有效,您可能需要调整比较运算符。


7

其他一些可能性:

if (in_array($value, range($min, $max), true)) {
    echo "You can be sure that $min <= $value <= $max";
}

或者:

if ($value === min(max($value, $min), $max)) {
    echo "You can be sure that $min <= $value <= $max";
}

实际上,这是用来将超出范围的值转换为最接近它的端点。
$value = min(max($value, $min), $max);

例子

/**
 * This is un-sanitized user input.
 */
$posts_per_page = 999;

/**
 * Sanitize $posts_per_page.
 */
$posts_per_page = min(max($posts_per_page, 5), 30);

/**
 * Use.
 */
var_dump($posts_per_page); // Output: int(30)

7
您可以尝试以下一行代码:
if (($x-$min)*($x-$max) < 0)

或者:

if (max(min($x, $max), $min) == $x)

1
min()max()将在实际硬件实现中使用比较,因此同时使用minmax以及单个比较将导致总共始终执行三次。相反,只需编写if($min < $x and $x < $max)即可,在最坏情况下执行两次比较,并且仅在值$x小于$min限制时才执行一次。乘法变体可能会更快,因为它可以非常有效地使用CPU流水线,但在PHP的情况下,我建议测试它,而不是假设它比带有快捷方式and的两个比较更好。 - Mikko Rantalainen

1
我创建了一个简单的辅助函数。
if ( !function_exists('number_between') )
{
    /**
     * number_between
     * 
     * @param {integer} $number
     * @param {array} $range [min, max]
     * @return {boolean}
     */
    function number_between(
            int $number, 
            array $range
    ){
        
        if(
                count($range) !== 2 || 
                is_numeric($range[0]) === FALSE || 
                is_numeric($range[1]) === FALSE
        ){
            throw new \Exception("number_between second parameter must contain two numbers.", E_WARNING);
        }
        
        if( 
                in_array($number, range($range[0], $range[1]))
        ){
            return TRUE;
        }else{
            return FALSE;
        }
    }
    
}

1
使用 switch case。
    switch ($num){

        case ($num>= $value1 && $num<= $value2): 
            echo "within range 1";
        break;
        case ($num>= $value3 && $num<= $value4): 
            echo "within range 2";
        break;
        .
        .
        .
        .
        .

        default: //default
            echo "within no range";
        break;
     }

5
应该是switch(true),否则如果$num == 0,case语句的逻辑会失败,因为PHP尝试匹配0 == ($num>= $value1 && $num<= $value2)等等。我已经建议将其作为编辑内容。 - Zane

0
我创建了一个函数来检查数组中的时间是否有重叠:
    /**
     * Function to check if there are overlapping times in an array of \DateTime objects.
     *
     * @param $ranges
     *
     * @return \DateTime[]|bool
     */
    public function timesOverlap($ranges) {
        foreach ($ranges as $k1 => $t1) {
            foreach ($ranges as $k2 => $t2) {
                if ($k1 != $k2) {
                    /* @var \DateTime[] $t1 */
                    /* @var \DateTime[] $t2 */
                    $a = $t1[0]->getTimestamp();
                    $b = $t1[1]->getTimestamp();
                    $c = $t2[0]->getTimestamp();
                    $d = $t2[1]->getTimestamp();

                    if (($c >= $a && $c <= $b) || $d >= $a && $d <= $b) {
                        return true;
                    }
                }
            }
        }

        return false;
    }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接