Operadores de Comparação

Operadores de comparação, como os seus nomes implicam, permitem que você compare dois valores. Você pode se interessar em ver as tabelas de comparação de tipos, que tem exemplo das várias comparações entre tipos relacionadas.

Operadores de comparação
Exemplo Nome Resultado
$a == $b Igual Verdadeiro (true) se $a é igual a $b.
$a === $b Idêntico Verdadeiro (true) se $a é igual a $b, e eles são do mesmo tipo.
$a != $b Diferente Verdadeiro se $a não é igual a $b.
$a <> $b Diferente Verdadeiro se $a não é igual a $b.
$a !== $b Não idêntico Verdadeiro de $a não é igual a $b, ou eles não são do mesmo tipo (introduzido no PHP4).
$a < $b Menor que Verdadeiro se $a é estritamente menor que $b.
$a > $b Maior que Verdadeiro se $a é estritamente maior que $b.
$a <= $b Menor ou igual Verdadeiro se $a é menor ou igual a $b.
$a >= $b Maior ou igual Verdadeiro se $a é maior ou igual a $b.
$a <=> $b Spaceship (nave espacial) Um integer menor que, igual a ou maior que zero quando $a é, respectivamente, menor que, igual a ou maior que $b. Disponível a partir do PHP 7.

Se comparar um número com uma string ou com strings numéricas, cada string é convertido para um número e então a comparação é realizada numericamente. Essas regras também se aplicam a instrução switch. As conversões de tipo não são realizadas quando a comparação utilizada é === ou !== por esse tipo de comparação envolver valores e tipos.

<?php
var_dump
(0 == "a"); // 0 == 0 -> true
var_dump("1" == "01"); // 1 == 1 -> true
var_dump("10" == "1e1"); // 10 == 10 -> true
var_dump(100 == "1e2"); // 100 == 100 -> true

switch ("a") {
case
0:
echo
"0";
break;
case
"a": // nunca é alcançado porque "a" já foi combinado com 0
echo "a";
break;
}
?>
<?php
// Integers
echo 1 <=> 1; // 0
echo 1 <=> 2; // -1
echo 2 <=> 1; // 1

// Floats
echo 1.5 <=> 1.5; // 0
echo 1.5 <=> 2.5; // -1
echo 2.5 <=> 1.5; // 1

// Strings
echo "a" <=> "a"; // 0
echo "a" <=> "b"; // -1
echo "b" <=> "a"; // 1

echo "a" <=> "aa"; // -1
echo "zz" <=> "aa"; // 1

// Arrays
echo [] <=> []; // 0
echo [1, 2, 3] <=> [1, 2, 3]; // 0
echo [1, 2, 3] <=> []; // 1
echo [1, 2, 3] <=> [1, 2, 1]; // 1
echo [1, 2, 3] <=> [1, 2, 4]; // -1

// Objects
$a = (object) ["a" => "b"];
$b = (object) ["a" => "b"];
echo
$a <=> $b; // 0

$a = (object) ["a" => "b"];
$b = (object) ["a" => "c"];
echo
$a <=> $b; // -1

$a = (object) ["a" => "c"];
$b = (object) ["a" => "b"];
echo
$a <=> $b; // 1

// only values are compared
$a = (object) ["a" => "b"];
$b = (object) ["b" => "b"];
echo
$a <=> $b; // 1

?>

Para vários tipos, comparações são feitas de acordo com a seguinte tabela (em ordem).

Comparação com vários tipos
Tipo do 1º operando Tipo do 2º operando Resultado
null ou string string Converte null para "", numérico ou comparação léxica
bool or null qualquer Converte para bool, false < true
object object Classes nativas podem definir como são comparadas, classes diferentes são incomparáveis, mesma classe - compara propriedades igual faz arrays (PHP 4), PHP 5 tem sua explicação
string, resource ou number string, resource ou number Transforma strings e resources para números
array array Array com menos membros é menor, se a chave do operando 1 não é encontrada no operando 2, então os arrays são incomparáveis, caso contrário - compara valor por valor (veja o seguinte exemplo)
object qualquer object é sempre maior
array qualquer array é sempre maior

Exemplo #1 Comparações de boolean e null

<?php
// Bool e null são sempre comparados como booleanos
var_dump(1 == TRUE); // TRUE - same as (bool)1 == TRUE
var_dump(0 == FALSE); // TRUE - same as (bool)0 == FALSE
var_dump(100 < TRUE); // FALSE - same as (bool)100 < TRUE
var_dump(-10 < FALSE);// FALSE - same as (bool)-10 < FALSE
var_dump(min(-100, -10, NULL, 10, 100)); // NULL - (bool)NULL < (bool)-100 is FALSE < TRUE
?>

Exemplo #2 Transcrição do padrão de comparação de array

<?php
// Arrays são comparados assim quando utilizando-se os operadores padrão
function standard_array_compare($op1, $op2)
{
if (
count($op1) < count($op2)) {
return -
1; // $op1 < $op2
} elseif (count($op1) > count($op2)) {
return
1; // $op1 > $op2
}
foreach (
$op1 as $key => $val) {
if (!
array_key_exists($key, $op2)) {
return
null; // uncomparable
} elseif ($val < $op2[$key]) {
return -
1;
} elseif (
$val > $op2[$key]) {
return
1;
}
}
return
0; // $op1 == $op2
}
?>

Veja também strcasecmp(), strcmp(), operadores de array, e a seção do manual sobre Tipos.

Aviso

Comparison of floating point numbers

Por conta da forma que floats são representados internamente não se deve testar dois floats com o comparador de igualdade.

Veja a documentação de float para mais detalhes.

Operador Ternário

Outro operador condicional é o operador "?:" (ou ternário).

Exemplo #3 Atribuindo um valor padrão

<?php
// Example usage for: Ternary Operator
$action = (empty($_POST['action'])) ? 'default' : $_POST['action'];

// The above is identical to this if/else statement
if (empty($_POST['action'])) {
$action = 'default';
} else {
$action = $_POST['action'];
}

?>
A expressão (expr1) ? (expr2) : (expr3) é avaliada para expr2 se expr1 é avaliada como true, ou expr3 se expr1 é avaliada como false.

Desde o PHP 5.3 é possível deixar vazia a parte central do operador ternário. A expressão expr1 ?: expr3 retorna expr1 se expr1 verdade true e expr3 do contrário.

Nota: Note que o operador ternário é uma expressão, e ele não é avaliado para uma variável, mas para o resultado de uma expressão. Isto é importante saber se você quer retornar uma variável por referência. A declaração return $var == 42 ? $a : $b; em uma função que retorna por referência conseqüêntemente não irá funcionar e será avisado.

Nota:

É recomendado para evitar "stacking" de expressões ternárias. O comportamento do PHP quando usando mais de um operador ternário no único comando não é óbvio:

Exemplo #4 Comportamento não óbvio do ternário

<?php
// o seguinte aparenta imprimir 'true'
echo (true?'true':false?'t':'f');

// conteudo, a saída acima é 't'
// isto por causa da expressão ternário se avaliada da esquerda pra direita

// o seguinte é a versão mais óbvia do mesmo código acima
echo ((true ? 'true' : 'false') ? 't' : 'f');

// aqui, você pode ver que a primeira expressão é avaliada para 'true', que
// por sua vez avalia para (bool)true, assim retornando a parte true da
// segunda expressão ternária.
?>

Operador Null Coalescing

Existe ainda o operador "??" (ou null coalescing), disponível desde o PHP 7.

Exemplo #5 Atribuindo um valor padrão

<?php
// Exemplo do operador Null Coalesce
$action = $_POST['action'] ?? 'default';

// O conteúdo acima é idêntico à essa declaração if/else
if (isset($_POST['action'])) {
$action = $_POST['action'];
} else {
$action = 'default';
}

?>
A expressão (expr1) ?? (expr2) é avaliada para expr2 se expr1 for null, e expr1 do contrário.

Esse operador em particular não emite aviso caso o valor da esquerda não exista, assim como isset(). Sendo especialmente útil em chaves de arrays.

Nota: Note que o operador null coalescing é uma expressão, e ele não é avaliado para uma variável, mas para o resultado de uma expressão. Isto é importante saber se você quer retornar uma variável por referência. A declaração return $foo ?? $bar; em uma função que retorna por referência conseqüêntemente não irá funcionar e será avisado.

Nota:

Note que o operador null coalescing permite a criação de aninhamentos simples:

Exemplo #6 Aninhando o operador null coalescing

<?php

$foo
= null;
$bar = null;
$baz = 1;
$qux = 2;

echo
$foo ?? $bar ?? $baz ?? $qux; // exibe 1

?>

add a note

User Contributed Notes 12 notes

up
163
crazy888s at hotmail dot com
13 years ago
I couldn't find much info on stacking the new ternary operator, so I ran some tests:

<?php
echo 0 ?: 1 ?: 2 ?: 3; //1
echo 1 ?: 0 ?: 3 ?: 2; //1
echo 2 ?: 1 ?: 0 ?: 3; //2
echo 3 ?: 2 ?: 1 ?: 0; //3

echo 0 ?: 1 ?: 2 ?: 3; //1
echo 0 ?: 0 ?: 2 ?: 3; //2
echo 0 ?: 0 ?: 0 ?: 3; //3
?>

It works just as expected, returning the first non-false value within a group of expressions.
up
4
admin at zeros dot co dot id
9 months ago
Please be careful when you try to compare strings that have a plus sign `+` at the beginning (such as phone number, etc). When you use the Equal operator `==` PHP will ignore the plus sign. Use Identical operator `===` instead

Example:

$str1 = "62";
$str2 = "+62";

var_dump($str1 == $str2); // bool(true)
var_dump($str1 === $str2); // bool(false)
up
4
Sumon Mahmud
3 years ago
Extending from here: https://www.php.net/manual/en/language.operators.comparison.php#121907

$a = ['a' => 1, 'b' => 2, 'c' => 3, 'e' => 4];
$b = ['a' => 1, 'b' => 2, 'd' => 3, 'e' => 4];

echo $a > $b; // 0
echo $b > $a; // 0
echo $a <$b; // 0
echo $b < $a; // 0

If using spaceship operator then it is returning true like :

echo $a <=> $b; //1
echo $b <=> $a; //1
echo $a <=> $b; //1
echo $b <=> $a; //1
up
20
adam at caucho dot com
17 years ago
Note: according to the spec, PHP's comparison operators are not transitive.  For example, the following are all true in PHP5:

"11" < "a" < 2 < "11"

As a result, the outcome of sorting an array depends on the order the elements appear in the pre-sort array.  The following code will dump out two arrays with *different* orderings:

<?php
$a
= array(2,    "a""11", 2);
$b = array(2,    "11", "a"2);
sort($a);
var_dump($a);
sort($b);
var_dump($b);
?>

This is not a bug report -- given the spec on this documentation page, what PHP does is "correct".  But that may not be what was intended...
up
16
rshawiii at yahoo dot com
17 years ago
You can't just compare two arrays with the === operator
like you would think to find out if they are equal or not.  This is more complicated when you have multi-dimensional arrays.  Here is a recursive comparison function.

<?php
/**
* Compares two arrays to see if they contain the same values.  Returns TRUE or FALSE.
* usefull for determining if a record or block of data was modified (perhaps by user input)
* prior to setting a "date_last_updated" or skipping updating the db in the case of no change.
*
* @param array $a1
* @param array $a2
* @return boolean
*/
function array_compare_recursive($a1, $a2)
{
   if (!(
is_array($a1) and (is_array($a2)))) { return FALSE;}   
   
   if (!
count($a1) == count($a2))
      {
       return
FALSE; // arrays don't have same number of entries
     
}
     
   foreach (
$a1 as $key => $val)
   {
       if (!
array_key_exists($key, $a2))
           {return
FALSE; // uncomparable array keys don't match
             
}
       elseif (
is_array($val) and is_array($a2[$key]))  // if both entries are arrays then compare recursive
          
{if (!array_compare_recursive($val,$a2[$key])) return FALSE;
           }
       elseif (!(
$val === $a2[$key])) // compare entries must be of same type.
          
{return FALSE;
           }
   }
   return
TRUE; // $a1 === $a2
}
?>
up
12
bishop
16 years ago
When you want to know if two arrays contain the same values, regardless of the values' order, you cannot use "==" or "===".  In other words:

<?php
(array(1,2) == array(2,1)) === false;
?>

To answer that question, use:

<?php
function array_equal($a, $b) {
    return (
is_array($a) && is_array($b) && array_diff($a, $b) === array_diff($b, $a));
}
?>

A related, but more strict problem, is if you need to ensure that two arrays contain the same key=>value pairs, regardless of the order of the pairs.  In that case, use:

<?php
function array_identical($a, $b) {
    return (
is_array($a) && is_array($b) && array_diff_assoc($a, $b) === array_diff_assoc($b, $a));
}
?>

Example:
<?php
$a
= array (2, 1);
$b = array (1, 2);
// true === array_equal($a, $b);
// false === array_identical($a, $b);

$a = array ('a' => 2, 'b' => 1);
$b = array ('b' => 1, 'a' => 2);
// true === array_identical($a, $b)
// true === array_equal($a, $b)
?>

(See also the solution "rshawiii at yahoo dot com" posted)
up
5
niall at maranelda dot org
5 years ago
Care must be taken when using the spaceship operator with arrays that do not have the same keys:

- Contrary to the notes above ("Example #2 Transcription of standard array comparison"), it does *not* return null if the left-hand array contains a key that the right-hand array does not.
- Because of this, the result depends on the order you do the comparison in.

For example:

<?php
$a
= ['a' => 1, 'b' => 2, 'c' => 3, 'e' => 4];
$b = ['a' => 1, 'b' => 2, 'd' => 3, 'e' => 4];

var_dump($a <=> $b);        // int(1) : $a > $b because $a has the 'c' key and $b doesn't.

var_dump($b <=> $a);        // int(1) : $b > $a because $b has the 'd' key and $a doesn't.
?>
up
5
Marcin Kuzawiski
7 years ago
A < B and still B < A...

$A = [1 => 1, 2 => 0, 3 => 1];
$B = [1 => 1, 3 => 0, 2 => 1];

var_dump($A < $B);  // TRUE
var_dump($B < $A);  // TRUE

var_dump($A > $B);  // TRUE
var_dump($B > $A);  // TRUE

Next - C and D are comparable, but neither C < D nor D < C (and still C != D)...

$C = [1 => 1, 2 => 1, 3 => 0];
$D = [1 => 1, 3 => 1, 2 => 0];

var_dump($C < $D); // FALSE
var_dump($D < $C); // FALSE

var_dump($C > $D); // FALSE
var_dump($D > $C); // FALSE

var_dump($D == $C); // FALSE
up
2
Tahazzot
2 years ago
Very careful when reading PHP documentation, Here's a lot of miss information.

According to documentation, They say's (int) 0 == (string) "a" is true. But it is not in PHP 8.

var_dump(0 == "a"); // 0 == 0 -> true

Now In PHP 8 it's False.
up
3
Ryan Mott
3 years ago
Searching for "double question mark" operator should find this page (and hopefully after this comment the crawlers will agree)
up
7
Cuong Huy To
11 years ago
In the table "Comparison with Various Types", please move the last line about "Object" to be above the line about "Array", since Object is considered to be greater than Array (tested on 5.3.3)

(Please remove my "Anonymous" post of the same content before. You could check IP to see that I forgot to type my name)
up
1
gfilippakis at sleed dot gr
2 months ago
Please note that using the null coalescing operator to check properties on a class that has the __get magic method (without an __isset magic method) invokes the magic method.

For example:

<?php

class A
{
    public function
__get($property)
    {
        echo
'Called __get for ' . $property . PHP_EOL;
    }
}

$a = new A();

echo
'Trying null coalescing operator' . PHP_EOL;
$b = $a->test ?? 5;

echo
'Trying isset()' . PHP_EOL;
if (isset(
$a->test)) {
   
$b = $a->test;
} else {
   
$b = 5;
}

?>
To Top