Operaciones aritméticas

Tipos de datos numéricos: enteros y decimales

Manual de PHP: Enteros - Decimales

PHP utiliza dos tipos de datos distintos para números: integer para números enteros y float para números decimales. Al escribir un número decimal, el separador entre la parte entera y la parte decimal es el punto (.), no la coma (,).

En PHP, los valores de enteros y decimales no pueden ser arbitrariamente grandes. Los valores máximos dependen de la arquitectura del procesador (32 o 64 bits), del sistema operativo y de la versión de PHP

Estos valores máximos (y otros relacionados) se guardan en varias constantes predefinidas (PHP_INT_MAX, PHP_FLOAT_MAX, etc), como se comenta en la lección Constantes y constantes predefinidas.

Si se necesita trabajar con enteros mayores que los valores máximos, es necesario utilizar las funciones bcmath.

Operaciones básicas

Los operadores aritméticos básicos son los siguientes:

Ejemplo Nombre Resultado
-$a Negación El opuesto de $a.
$a + $b Suma Suma de $a y $b.
$a - $b Resta Diferencia entre $a y $b.
$a * $b Multiplicación Producto de $a y $b.
$a / $b División Cociente de $a y $b.
$a ** $b Potenciación $a elevado a $b.

En general, el resultado de una operación es un número decimal si al menos uno de los números implicados es decimal. El resultado de una operación es entero solo cuando todos los números implicados son enteros, excepto si se trata de una división que da un resultado decimal o si el resultado es demasiado grande para representarlo mediante un entero.

Si el resultado de un cálculo con números enteros es demasiado grande para poderse representar con un entero, PHP lo convierte automáticamente en decimal, perdiéndose precisión.

<?php
print "<p>PHP_INT_MAX = " . PHP_INT_MAX . "</p>\n";
print "\n";
print "<p>PHP_INT_MAX - 1 = " . PHP_INT_MAX - 1 . "</p>\n";
print "\n";
print "<p>PHP_INT_MAX + 1 = " . PHP_INT_MAX + 1 . "</p>\n";
?>
Enlace a ejemplo

Si el resultado de un cálculo con números decimales es demasiado grande para poderse representar con un decimal, PHP lo convierte automáticamente en la constante INF.

<?php
print "<p>PHP_FLOAT_MAX = " . PHP_FLOAT_MAX . "</p>\n";
print "\n";
print "<p>PHP_FLOAT_MAX - 1 = " . PHP_FLOAT_MAX - 1E292 . "</p>\n";
print "\n";
print "<p>PHP_FLOAT_MAX + 1 = " . PHP_FLOAT_MAX + 1E292 . "</p>\n";
?>
Enlace a ejemplo

Cociente y resto de una división

El cociente y resto de una división están relacionados con el dividendo y divisor mediante la fórmula:

Cociente y resto de una división

Ejemplo Nombre Resultado
$a % $b Módulo / Resto Resto de $a dividido por $b.
  • Si algún número es decimal, se trunca a entero antes de efectuar el cálculo. Por ejemplo, 5 % 2.5 da como resultado 1 y no 0 porque calcula el resto de 5 entre 2, no el resto de 5 entre 2.5.
  • El resultado tiene el mismo signo que el dividendo. Por ejemplo, -5 % 2 da como resultado -1, pero 5 % -2 da como resultado 1.
intdiv($a, $b) Cociente Cociente de $a dividido por $b.
  • No se trata de un operador, sino de una función, pero se incluye aquí por tratarse de una operación básica.
  • Si algún número es decimal, se trunca a entero antes de efectuar el cálculo. Por ejemplo, intdiv(5, 2.7) da como resultado 1 y no 2.3 porque calcula el resto de 5 entre 2, no el resto de 5 entre 2.7.

Nota: Como se comenta en la lección Varios, el cociente y el divisor de una división en la que intervienen números enteros negativos no se calcula de la misma manera en los distintos lenguajes de programación.


La función fmod calcula el resto de una división con números decimales

<?php
print "<p>El resto de 17 dividido entre 3.1 es " . fmod(17, 3.1) . "</p>\n";
?>
  
<p>El resto de 17 dividido entre 3.1 es 1.5</p>

Potencias y raíces

El operador ** calcula potencias y raíces. PHP también dispone de la función pow(x, y) para calcular potencias y raíces.

<?php
print "<p>2<sup>3</sup> = " . 2 ** 3 . "</p>\n";
print "\n";
print "<p>2<sup>3</sup> = " . pow(2, 3) . "</p>\n";
?>

23 = 8

23 = 8

Tanto el operador como la función permiten calcular raíces, teniendo en cuenta que una raíz n-ésima es una potencia 1/n.

<?php
print "<p>La raíz cuadrada de 25 es " . 25 ** (1 / 2) . "</p>\n";
print "\n";
print "<p>La raíz cuadrada de 25 es " . 25 ** 0.5 . "</p>\n";
print "\n";
print "<p>La raíz cuadrada de 25 es " . pow(25, 1 / 2) . "</p>\n";
print "\n";
print "<p>La raíz cuadrada de 25 es " . pow(25, 0.5) . "</p>\n";
print "\n";
print "<p>La raíz cúbica de 1000 es " . 1000 ** (1 / 3) . "</p>\n";
print "\n";
print "<p>La raíz cúbica de 1000 es " . pow(1000, 1 / 3) . "</p>\n";
?>
<p>La raíz cuadrada de 25 es 5</p>

<p>La raíz cuadrada de 25 es 5</p>

<p>La raíz cuadrada de 25 es 5</p>

<p>La raíz cuadrada de 25 es 5</p>

<p>La raíz cúbica de 1000 es 10</p>

<p>La raíz cúbica de 1000 es 10</p>

En el caso de las raíces cuadradas, se puede utilizar también la función sqrt(x).

<?php
print "<p>La raíz cuadrada de 25 es " . sqrt(25) . "</p>\n";
?>
<p>La raíz cuadrada de 25 es 5</p>

Operadores de incremento y decremento

Ejemplo Nombre Efecto
++$a Pre-incremento Incrementa $a en uno, y luego devuelve $a.
$a++ Post-incremento Devuelve $a, y luego incrementa $a en uno.
--$a Pre-decremento Decrementa $a en uno, luego devuelve $a.
$a-- Post-decremento Devuelve $a, luego decrementa $a en uno.

La diferencia entre el pre-incremento y el post-incremento es que en el primer caso primero se incrementa la variable y después se utiliza y en el segundo primero se utiliza y después se incrementa.

<?php
$valor = 9;
print "<p>" . ++$valor . "</p>\n";
?>
<p>10</p>
<?php
$valor = 9;
print "<p>" . $valor++ . "</p>\n";
?>
<p>9</p>

El operador de incremento funciona también con caracteres, teniendo en cuenta que al incrementar el carácter 'z' se obtiene la cadena 'aa'. El operador de decremento no funciona con caracteres.

<?php
$valor = "b";
print "<p>" . ++$valor . "</p>\n";
?>
<p>c</p>
<?php
$valor = "z";
print "<p>" . ++$valor . "</p>\n";
?>
<p>aa</p>
<?php
$valor = "a9z";
print "<p>" . ++$valor . "</p>\n";
?>
<p>b0a</p>

Paréntesis

Los operadores aritméticos tienen el mismo orden de precedencia que en Matemáticas. Concretamente, el orden de precedencia de los operadores comentados anteriormente es, de mayor a menor, el siguiente (los operadores indicados en el mismo grupo se efectúan en el orden en que aparecen en la expresión):

Los paréntesis permiten agrupar operaciones de manera que las operaciones entre paréntesis se realicen antes que las operaciones fuera de los paréntesis. Se aconseja no utilizar paréntesis cuando las operaciones den el mismo resultado con o sin paréntesis.

Operadores combinados

Los operadores combinados permiten simplificar algunas expresiones de asignación:

Ejemplo Nombre Equivale a
$a += $b Suma $a = $a + $b
$a -= $b Resta $a = $a - $b
$a *= $b Multiplicación $a = $a * $b
$a /= $b División $a = $a / $b
$a %= $b Módulo $a = $a % $b

Redondear un número

La función round(x) redondea el número x al entero más próximo. En los valores intermedios (,5), redondea hacia arriba los valores positivos y hacia abajo los negativos.

<?php
print "<p>2.6 se redondea con round() a " . round(2.6) . "</p>\n";
print "<p>2.3 se redondea con round() a " . round(2.3) . "</p>\n";
print "<p>2.5 se redondea con round() a " . round(2.5) . "</p>\n";
print "<p>-2.6 se redondea con round() a " . round(-2.6) . "</p>\n";
print "<p>-2.3 se redondea con round() a " . round(-2.3) . "</p>\n";
print "<p>-2.5 se redondea con round() a " . round(-2.5) . "</p>\n";
?>
<p>2.6 se redondea con round() a 3</p>
<p>2.3 se redondea con round() a 2</p>
<p>2.5 se redondea con round() a 3</p>
<p>-2.6 se redondea con round() a -3</p>
<p>-2.3 se redondea con round() a -2</p>
<p>-2.5 se redondea con round() a -3</p>

La función round() se puede utilizar para verificar si un número es un número entero (positivo o negativo), comprobando si un número coincide con su valor redondeado.

<?php
$numero = 4.3;
if ($numero == round($numero)) {
    print "<p>$numero es un número entero</p>\n";
} else {
    print "<p>$numero no es un número entero</p>\n";
}

$numero = -6;
if ($numero == round($numero)) {
    print "<p>$numero es un número entero</p>\n";
} else {
    print "<p>$numero no es un número entero</p>\n";
}
?>
<p>4.3 no es un número entero</p>
<p>-6 es un número entero</p>

La función round(x,n) redondea x con n decimales (si n es negativo redondea a decenas, centenas, etc.).

<?php
print "<p>2.6574 se redondea con round() con dos decimales a " . round(2.6574, 2) . "</p>\n";
print "<p>3141592 redondeado con round() con centenas es " . round(3141592, -2) . "</p>\n";
?>
<p>2.6574 se redondea con round() con dos decimales a 2.66</p>
<p>3141592 redondeado con round() con centenas es 3141600</p>

La función floor(x) redondea el número x al entero inferior (es decir, devuelve la parte entera).

<?php
print "<p>2.6 se redondea con floor() a " . floor(2.6) . "</p>\n";
print "<p>2.3 se redondea con floor() a " . floor(2.3) . "</p>\n";
print "<p>-2.6 se redondea con floor() a " . floor(-2.6) . "</p>\n";
print "<p>-2.3 se redondea con floor() a " . floor(-2.3) . "</p>\n";
?>
<p>2.6 se redondea con floor() a 2</p>
<p>2.3 se redondea con floor() a 2</p>
<p>-2.6 se redondea con floor() a -3</p>
<p>-2.3 se redondea con floor() a -3</p>

La función ceil(x) redondea el número x al entero superior.

<?php
print "<p>2.6 se redondea con ceil() a " . ceil(2.6) . "</p>\n";
print "<p>2.3 se redondea con ceil() a " . ceil(2.3) . "</p>\n";
print "<p>-2.6 se redondea con ceil() a " . ceil(-2.6) . "</p>\n";
print "<p>-2.3 se redondea con ceil() a " . ceil(-2.3) . "</p>\n";
?>
<p>2.6 se redondea con ceil() a 3</p>
<p>2.3 se redondea con ceil() a 3</p>
<p>-2.6 se redondea con ceil() a -2</p>
<p>-2.3 se redondea con ceil() a -2</p>

Máximo y mínimo

Las funciones max() y min() devuelven el máximo y el mínimo, respectivamente, de una lista o matriz de valores..

<?php
print "<p>El máximo es " . max(20, 40, 25.1, 14.7) . "</p>\n";
?>
<p>El máximo es 40</p>
<?php
print "<p>El mínimo es " . min(20, 40, 25.1, 14.7) . "</p>\n";
?>
<p>El mínimo es 14.7</p>
<?php
$datos = [20, 40, 25.1, 14.7];
print "<p>El mínimo es " . min($datos) . "</p>\n";
?>
<p>El mínimo es 14.7</p>

Formatear un número

Para escribir un número con los símbolos de separación de decimales y de miles españoles, es decir, una coma (,) para separar la parte entera de la decimal y un punto (.) para separar las cifras de la parte entera en grupos de tres, se puede utilizar la función number_format().

<?php
print "<p>" . number_format(1300, 5) . "</p>\n";
?>
<p>1,300.00000</p>
<?php
print "<p>" . number_format(123456.789, 2) . "</p>\n";
?>
<p>123,456.79</p>
<?php
print "<p>" . number_format(123456789123, 0, ",", ".") . "</p>\n";
?>
<p>123.456.789.123</p>
<?php
print "<p>" . number_format(123456789123456.789, 2, ",", ".") . "</p>\n";
?>
<p>123.456.789.123.456,78</p>

La función requiere dos o cuatro argumentos:

La función devuelve el número formateado. Si sólo se utilizan dos argumentos, se utiliza el punto como separador de parte entera y decimal y la coma como separador de miles (notación inglesa).

Números aleatorios

Para obtener un número entero aleatorio entre dos valores determinados, se puede utilizar la función rand(), aunque esta función genera números aleatorios que no se pueden considerar criptográficamente seguros. En caso de necesitarse valores seguros, se puede utilizar la función random_int(), incorporada en PHP 7.0.

La función rand() admite dos argumentos:

<?php
print "<p>" . rand(1, 6) . "</p>\n";
print "<p>" . rand(100, 150) . "</p>\n";
print "<p>" . rand(-20, -10) . "</p>\n";
?>
<p>5</p>
<p>135</p>
<p>-20</p>

Si se llama a la función sin argumentos, esta devuelve un número entero aleatorio entre 0 y 2147483647. El valor 2147483647 (231 - 1) se debe a que PHP genera los números aleatorios mediante la versión de 32 bits del algoritmo Mersenne Twister y el valor 2147483647 es el mayor que puede almacenar PHP en una variable entera (véase PHP_INT_MAX).

<?php
print "<p>" . getrandmax() . "</p>\n";
print "<p>" . rand() . "</p>\n";
print "<p>" . rand() . "</p>\n";
?>
<p>2147483647</p>
<p>1334990778</p>
<p>19794827</p>