Cómo escribir condicionales en Kotlin

1. Antes de comenzar

Los condicionales son una de las bases más importantes de la programación. Son comandos en lenguajes de programación que manejan decisiones. Con ellos, el código es dinámico, lo que significa que puede comportarse de manera diferente según una condición diferente.

En este codelab, aprenderás a usar las sentencias y expresiones if/else y when para escribir condicionales en Kotlin.

Requisitos previos

  • Conocimientos de los conceptos básicos de programación de Kotlin, incluidas las variables, y las funciones println() y main()

Qué aprenderás

  • Cómo escribir expresiones booleanas
  • Cómo escribir sentencias if/else
  • Cómo escribir sentencias when
  • Cómo escribir expresiones if/else
  • Cómo escribir expresiones when
  • Cómo usar comas a fin de definir el comportamiento común para varias ramas en condicionales when
  • Cómo usar el rango in a fin de definir el comportamiento común para un rango de ramas en condicionales when
  • Cómo usar la palabra clave is para escribir sentencias condicionales when

Requisitos

  • Un navegador web con acceso a Playground de Kotlin

2. Cómo usar sentencias if/else para expresar condiciones

En la vida, es común hacer las cosas de manera diferente según la situación a la que te enfrentes. Por ejemplo, si hace frío, usas una chaqueta, mientras que, si hace calor, te la quitas.

Diagrama de flujo en el que se describe una decisión que se toma cuando hace frío. Una flecha de afirmación apunta a un mensaje que indica "Llevar chaqueta" y una flecha de negación apunta al mensaje "No llevar chaqueta".

La toma de decisiones también es un concepto fundamental en la programación. Escribes instrucciones sobre cómo debe comportarse un programa en una situación determinada para que pueda actuar o reaccionar de manera adecuada cuando se produzca la situación. En Kotlin, cuando quieras que tu programa realice diferentes acciones según una condición, puedes usar una sentencia if/else. En la siguiente sección, escribirás una sentencia if.

Cómo escribir condiciones if con expresiones booleanas

Imagina que creas un programa que les indica a los conductores lo que deben hacer cuando están detenidos en un semáforo. Enfócate en la primera condición: un semáforo en rojo. ¿Qué haces en un semáforo en rojo? Te detienes.

Diagrama de flujo en el que se describe una decisión tomada cuando el color del semáforo es rojo. Una flecha de afirmación apunta a un mensaje que indica "Detenerse".

En Kotlin, puedes expresar esta condición con una sentencia if. Observa la anatomía de una sentencia if:

Un diagrama que describe una sentencia if con la palabra clave if seguida de un par de paréntesis con una condición dentro de ella. Después de eso, hay un par de llaves con el cuerpo. Se destaca el bloque de condición.

Para usar sentencias if, debes usar la palabra clave if seguida de la condición que deseas evaluar. Debes expresar la condición con una expresión booleana. Las expresiones combinan valores, variables y operadores que muestran un valor. Las expresiones booleanas muestran un valor booleano.

Anteriormente, aprendiste sobre los operadores de asignación, como los siguientes:

val number = 1

El operador de asignación = asigna un valor 1 a la variable number.

En cambio, las expresiones booleanas se construyen con operadores de comparación, que comparan valores o variables en ambos lados de la ecuación. El siguiente es un operador de comparación.

1 == 1

El operador de comparación == compara los valores entre sí. ¿Qué valor booleano crees que muestra esta expresión?

Busca el valor booleano de esta expresión:

  1. Usa Playground de Kotlin para ejecutar tu código.
  2. En el cuerpo de la función, agrega una función println() y, luego, pasa la expresión 1 == 1 como argumento:
fun main() {
    println(1 == 1)
}
  1. Ejecuta el programa y, luego, observa el resultado:
true

El primer valor 1 es igual al segundo valor 1, por lo que la expresión booleana muestra un valor true, que es un valor booleano.

Ponlo a prueba

Además del operador de comparación ==, hay operadores de comparación adicionales que puedes usar para crear expresiones booleanas:

  • Menor que: <
  • Mayor que: >
  • Menor o igual que: <=
  • Mayor o igual que: >=
  • No igual a: !=

Practica el uso de operadores de comparación con expresiones simples:

  1. En el argumento, reemplaza el operador de comparación == por el operador de comparación <:
fun main() {
    println(1 < 1)
}
  1. Ejecuta el programa y, luego, observa el resultado:

El resultado muestra un valor false porque el primer valor 1 no es menor que el segundo valor 1.

false
  1. Repite los dos primeros pasos con los otros números y operadores de comparación.

Cómo escribir una sentencia if simple

Ahora que viste algunos ejemplos de cómo escribir expresiones booleanas, puedes escribir tu primera sentencia if. La sintaxis de una sentencia if es la siguiente:

Un diagrama que describe una sentencia if con la palabra clave if seguida de un par de paréntesis con una condición dentro de ella. Después de eso, hay un par de llaves con un cuerpo. El bloque de cuerpo está destacado.

Una sentencia if comienza con la palabra clave if seguida de una condición, que es una expresión booleana entre paréntesis y un conjunto de llaves. El cuerpo es una serie de sentencias o expresiones que se colocan dentro de un par de llaves después de la condición. Estas instrucciones o expresiones solo se ejecutan cuando se cumple la condición. En otras palabras, las sentencias dentro de las llaves solo se ejecutan cuando una expresión booleana en la rama if muestra un valor true.

Escribe una sentencia if para la condición de semáforo en rojo:

  1. Dentro de la función main(), crea una variable trafficLightColor y asígnale un valor "Red":
fun main() {
    val trafficLightColor = "Red"
}
  1. Agrega una sentencia if para la condición de semáforo en rojo y, luego, pasa una expresión trafficLightColor == "Red":
fun main() {
    val trafficLightColor = "Red"

    if (trafficLightColor == "Red") {

    }
}
  1. En el cuerpo de la sentencia if, agrega una función println() y, luego, pasa un argumento "Stop":
fun main() {
    val trafficLightColor = "Red"

    if (trafficLightColor == "Red") {
        println("Stop")
    }
}
  1. Ejecuta el programa y, luego, observa el resultado:
Stop

La expresión trafficLightColor == "Red" muestra un valor true, por lo que se ejecuta la sentencia println("Stop"), que imprime el mensaje Stop.

Un diagrama que destaca la sentencia if de trafficLightColor == "Red" como condición y expresión booleana. En la siguiente línea, se observa que el cuerpo println("Stop") solo se ejecuta cuando la expresión booleana es verdadera.

Cómo agregar una rama else

Ahora puedes extender el programa para que le indique a los conductores que deben avanzar cuando el semáforo no esté en rojo.

Diagrama de flujo en el que se describe una decisión tomada cuando el color del semáforo es rojo. Una flecha de afirmación apunta a un mensaje que indica "Detenerse". Una flecha de negación que apunta a un mensaje que indica "Avanzar".

Debes agregar una rama else para crear una sentencia if/else. Una rama es una parte incompleta del código que puedes unir para formar sentencias o expresiones. Una rama else debe estar a continuación de una rama if.

Un diagrama que describe una sentencia if/else con la palabra clave if seguida de paréntesis con una condición dentro de ella. Después de eso, hay un par de llaves con el cuerpo 1 dentro de ellas seguido de una palabra clave else seguida de paréntesis. Después de eso, hay un par de llaves con un bloque de cuerpo 2 dentro.

Después de la llave de cierre de la sentencia if, agrega la palabra clave else seguida de un par de llaves. Dentro de las llaves de la sentencia else, puedes agregar un segundo cuerpo que solo se ejecute cuando la condición de la rama if sea falsa.

Agrega una rama else a tu programa:

  1. Después de la llave de cierre de la sentencia if, agrega la palabra clave else seguida de otro par de llaves:
fun main() {
    val trafficLightColor = "Red"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else {

    }
}
  1. Dentro de las llaves de la palabra clave else, agrega una función println() y, luego, pasa un argumento "Go":
fun main() {
    val trafficLightColor = "Red"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else {
        println("Go")
    }
}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Stop

El programa sigue comportándose como lo hacía antes de que agregaras la rama else, pero no imprime un mensaje Go.

  1. Reasigna la variable trafficLightColor a un valor Green porque deseas que los conductores avancen cuando el semáforo esté en verde:
fun main() {
    val trafficLightColor = "Green"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else {
        println("Go")
    }
}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Go

Como puedes ver, ahora el programa imprime un mensaje Go en lugar de un mensaje Stop.

Un diagrama que destaca la sentencia if/else con la condición trafficLightColor == "Red" anotada como la expresión booleana. El cuerpo println("Stop") solo se ejecuta cuando la expresión booleana es verdadera. Dentro de la cláusula else, se observa que la sentencia println("Go") solo se ejecuta cuando la expresión booleana es falsa.

Reasignaste la variable trafficLightColor a un valor "Green", por lo que la expresión trafficLightColor == "Red" evaluada en la rama if muestra un valor false ya que el valor "Green" no es igual al valor "Red".

Como resultado, el programa omite todas las sentencias de la rama if y, en su lugar, ejecuta todas las sentencias dentro de la rama else. Esto significa que se ejecuta la función println("Go"), pero no la función println("Stop").

Cómo agregar una rama else if

Por lo general, un semáforo tiene una luz amarilla que les indica a los conductores que procedan lentamente. Puedes expandir el proceso de toma de decisiones del programa para reflejarlo.

Diagrama de flujo en el que se describe una decisión tomada cuando el color del semáforo es rojo. Una flecha de afirmación apunta a un mensaje que indica "Detenerse". Una flecha de negación apunta a otra decisión tomada cuando el color del semáforo era amarillo. Una flecha de afirmación a partir de ese punto de decisión apunta a un mensaje "Despacio" y una flecha de negación apunta a "Avanzar".

Aprendiste a escribir condicionales que se adaptan a un solo punto de decisión con sentencias if/else que contienen una sola rama if y una sola rama else. ¿Cómo se puede manejar una rama más compleja con varios puntos de decisión? Cuando tienes varios puntos de decisión, debes crear condicionales con varias capas de condiciones. Puedes hacerlo agregando ramas else if a las sentencias if/else.

Después de la llave de cierre de la rama if, debes agregar la palabra clave else if. Dentro de los paréntesis de la palabra clave else if, debes agregar una expresión booleana como condición de la rama else if seguida de un cuerpo dentro de un par de llaves. El cuerpo solo se ejecuta si falla la condición 1, pero se cumple la condición 2.

Un diagrama que describe una sentencia if/else con la palabra clave if seguida de paréntesis con un bloque de condición 1 dentro de ella. Después de eso, hay un par de llaves con un cuerpo 1.   A continuación se muestra una palabra clave else/if si está entre paréntesis con un bloque de condición 2. Luego, se incluye un par de llaves con un bloque de cuerpo 2 dentro.  Después, hay una palabra clave else con otro par de llaves y un bloque de cuerpo 3 dentro.

La rama else if siempre se encuentra después de la rama if, pero antes de la rama else. Puedes usar varias ramas else if en una instrucción:

Un diagrama que muestra una condición if/else con varias ramas else/if entre las ramas if y else. Un texto anotado alrededor de las ramas else/if indica que hay varias ramas else/if.

La sentencia if también puede contener la rama if y la rama else if sin ninguna rama else:

Un diagrama que describe una sentencia if/else con la palabra clave if seguida de paréntesis con un bloque de condición 1 dentro de ella. Después de eso, hay un par de llaves con un cuerpo 1.   A continuación se muestra una palabra clave else/if si está entre paréntesis con un bloque de condición 2. Luego, se incluye un par de llaves con un bloque de cuerpo 2 dentro.

Agrega una rama else if a tu programa:

  1. Después de la llave de cierre de la sentencia if, agrega una expresión else if (trafficLightColor == "Yellow") seguida de llaves:
fun main() {
    val trafficLightColor = "Green"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {

    } else {
        println("Go")
    }
}
  1. Dentro de las llaves de la rama else if, agrega una sentencia println() y, luego, pasa un argumento de string "Slow":
fun main() {
    val trafficLightColor = "Green"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else {
        println("Go")
    }
}
  1. Reasigna la variable trafficLightColor a un valor de string "Yellow":
fun main() {
    val trafficLightColor = "Yellow"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else {
        println("Go")
    }
}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Slow

Ahora el programa imprime un mensaje Slow, en lugar de un mensaje Stop o Go.

Un diagrama que destaca la sentencia if/else con la condición trafficLightColor == "Red" en la cláusula if se indica como expresión booleana 1 y trafficLightColor == "Yellow" se indica como expresión booleana 2. El cuerpo println("stop") se anota solo para ejecutarse cuando la expresión booleana 1 es verdadera. Se indica que el cuerpo println("slow") solo se ejecuta cuando la expresión booleana 1 es falsa, pero la expresión booleana 2 es verdadera. Se indica que el cuerpo println("go") solo se ejecuta cuando las sentencias booleanas 1 y 2 son falsas.

Aquí se explica por qué solo imprime un mensaje Slow y no las otras líneas:

  • A la variable trafficLightColor se le asigna un valor "Yellow".
  • El valor "Yellow" no es igual al valor "Red", por lo que la expresión booleana de la rama if (indicada como 1 en la imagen) muestra un valor false. El programa omite todas las sentencias dentro de la rama if y no imprime un mensaje Stop.
  • Como la rama if produce un valor false, el programa procede a evaluar la expresión booleana dentro de la rama else if.
  • El valor "Yellow" es igual al valor "Yellow", por lo que la expresión booleana de la rama else if (denotada como 2 en la imagen) muestra un valor true. El programa ejecuta todas las sentencias dentro de la rama else if e imprime un mensaje Slow.
  • Como el valor booleano expression de la rama else if muestra un valor true, el programa omite el resto de las ramas. Por lo tanto, no se ejecutan todas las sentencias de la rama else y el programa no imprime un mensaje Go.

Ponlo a prueba

¿Notaste que el programa actual contiene un error?

En la Unidad 1, aprendiste un tipo de error llamado error de compilación en el que Kotlin no puede compilar el código debido a un error de sintaxis en tu código y no se puede ejecutar el programa. Aquí, se encuentra otro tipo de error llamado error lógico en el que se puede ejecutar el programa, pero no produce un resultado previsto.

Es probable que solo quieras que los conductores conduzcan cuando el semáforo esté de color verde. ¿Qué pasa si el semáforo está roto y no funciona? ¿Deseas que el conductor conduzca o reciba una advertencia de que algo anda mal?

Lamentablemente, en el programa actual, si el color del semáforo es else (otro), distinto de rojo o amarillo, se recomienda que el conductor avance.

Soluciona este problema:

  1. Reasigna la variable trafficLightColor a un valor "Black" para ilustrar un semáforo que está apagado:
fun main() {
    val trafficLightColor = "Black"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else {
        println("Go")
    }
}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Go

Ten en cuenta que el programa imprime un mensaje Go, aunque a la variable trafficLightColor no se le asigne un valor "Green". ¿Puedes corregir este programa para que refleje el comportamiento correcto?

Diagrama de flujo en el que se describe una decisión tomada cuando el color del semáforo es rojo. Una flecha de afirmación apunta a un mensaje que indica "Detenerse". Una flecha de negación apunta a otra decisión tomada cuando el color del semáforo era amarillo. Una flecha de afirmación desde esa decisión apunta a un mensaje "Despacio" y una flecha "No" apunta a otra decisión tomada cuando el color del semáforo es verde. Una flecha de afirmación a partir de esa decisión apunta a un mensaje "Avanzar", mientras que una flecha de negación apunta a un mensaje "Color no válido".

Debes modificar el programa para que imprima lo siguiente:

  • Un mensaje Go solo cuando a la variable trafficLightColor se le asigna un valor "Green".
  • Un mensaje Invalid traffic-light color cuando a la variable trafficLightColor no se le asigna un valor "Red", "Yellow" ni "Green".

Cómo corregir la rama else

La rama else siempre se encuentra al final de una sentencia if/else porque es una rama genérica. Se ejecuta de forma automática cuando no se cumplen todas las demás condiciones de las ramas anteriores. Como tal, la rama else no es adecuada cuando deseas que una acción se ejecute solo cuando satisfaga una condición específica. En el caso del semáforo, puedes usar la rama else if para especificar la condición de semáforos en verde.

Usa la rama else if para evaluar la condición de semáforo en luz verde:

  1. Después de la rama else if actual, agrega otra rama else if (trafficLightColor == "Green"):
fun main() {
    val trafficLightColor = "Black"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else if (trafficLightColor == "Green") {
        println("Go")
    }
}
  1. Ejecuta este programa y, luego, visualiza el resultado.

El resultado está vacío porque no tienes una rama else que se ejecute cuando no se cumplan las condiciones anteriores.

  1. Después de la última rama else if, agrega una rama else con una sentencia println("Invalid traffic-light color") dentro:
fun main() {
    val trafficLightColor = "Black"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else if (trafficLightColor == "Green") {
        println("Go")
    } else {
        println("Invalid traffic-light color")
    }

}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Invalid traffic-light color
  1. Asigna a la variable trafficLightColor otro valor además de "Red", "Yellow" o "Green", y vuelve a ejecutar el programa.

¿Cuál es el resultado del programa?

Como buena práctica de programación, sugerimos tener una rama else if explícita como validación de entrada para el color verde y una rama else para detectar otras entradas no válidas. De esta manera, se garantiza que los conductores avancen solo cuando el semáforo esté en verde. Para otros casos, hay un mensaje explícito que retransmite que el semáforo no se comporta de la manera esperada.

3. Cómo usar una sentencia when para varias ramas

Tu programa trafficLightColor se ve más complejo con varias condiciones, también conocidas como ramas. Es posible que se pregunte si puedes simplificar un programa con una cantidad aún mayor de ramas.

En Kotlin, cuando trabajas con varias ramas, puedes usar la sentencia when en lugar de if/else, ya que mejora la legibilidad. De esta manera, es más fácil para los lectores humanos, por lo general, los desarrolladores, leer el código. Es muy importante considerar la legibilidad cuando escribes el código, ya que es probable que otros desarrolladores lo revisen y modifiquen durante su vida útil. Una buena legibilidad garantiza que los desarrolladores entiendan correctamente tu código y no introduzcan errores en él de manera inadvertida.

Se prefieren las sentencias when cuando hay más de dos ramas para considerar.

Diagrama en el que se muestra la anatomía de una sentencia when. Comienza con una palabra clave when seguida de un par de llaves con un bloque de parámetros dentro de ellas. A continuación, dentro de un par de llaves, hay tres líneas de casos. Dentro de cada línea, hay un bloque de condición seguido de un símbolo de flecha y un bloque de cuerpo. Tenga en cuenta que cada una de las líneas de casos se evalúan de forma secuencial.

Una sentencia when acepta un solo valor a través del parámetro. Luego, el valor se evalúa frente a cada una de las condiciones de manera secuencial. A continuación, se ejecuta el cuerpo de la primera condición que se cumple. Cada condición y cuerpo están separados por una flecha (->). Al igual que con las sentencias if/else, cada par de condición y cuerpo se denomina rama en las sentencias when. Del mismo modo que ocurre con la sentencia if/else, puedes agregar una rama else como tu condición final en una sentencia when que funciona como una rama genérica.

Cómo volver a escribir una sentencia if/else con una sentencia when

En el programa de semáforos, ya existen muchas ramas:

  • Color de semáforo rojo
  • Color de semáforo amarillo
  • Color de semáforo verde
  • Otro color de semáforo

Convierte el programa para usar una sentencia when:

  1. En la función main(), quita la sentencia if/else:
fun main() {
    val trafficLightColor = "Black"

}
  1. Agrega una sentencia when y, luego, pasa la variable trafficLightColor como argumento:
fun main() {
    val trafficLightColor = "Black"

    when (trafficLightColor) {
    }
}
  1. En el cuerpo de la sentencia when, agrega la condición "Red" seguida de una flecha y un cuerpo println("Stop"):
fun main() {
    val trafficLightColor = "Black"

    when (trafficLightColor) {
        "Red" -> println("Stop")
    }
}
  1. En la siguiente línea, agrega la condición "Yellow" seguida de una flecha y un cuerpo println("Slow"):
fun main() {
    val trafficLightColor = "Black"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow" -> println("Slow")
    }
}
  1. En la siguiente línea, agrega la condición "Green" seguida de una flecha y un cuerpo println("Go"):
fun main() {
    val trafficLightColor = "Black"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow" -> println("Slow")
        "Green" -> println("Go")
    }
}
  1. En la siguiente línea, agrega la palabra clave else, seguida de una flecha y, luego, un cuerpo println("Invalid traffic-light color"):
fun main() {
    val trafficLightColor = "Black"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}
  1. Reasigna la variable trafficLightColor a un valor "Yellow":
fun main() {
    val trafficLightColor = "Yellow"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}

Cuando ejecutes este programa, ¿cuál crees que será el resultado?

  1. Ejecuta el programa y, luego, observa el resultado:
Slow

Un diagrama que anota la sentencia when La línea "Red" -> println("Stop") se anota como caso 1. La línea "Yellow" -> println("Slow") se anota como caso 2. La línea "Green" -> println("Go") se anota como caso 3. La línea "else" -> println("Invalid traffic-light color") se anota como caso 4.

El resultado es un mensaje Slow porque:

  • A la variable trafficLightColor se le asigna un valor "Yellow".
  • El programa evalúa cada condición, una por una, en secuencia.
  • El valor "Yellow" no es igual al valor "Red", por lo que el programa omite el primer cuerpo.
  • El valor "Yellow" es igual al valor "Yellow", por lo que el programa ejecuta el segundo cuerpo y, luego, imprime un mensaje Slow.
  • Se ejecutó un cuerpo, por lo que el programa ignora la tercera y cuarta rama, y abandona la sentencia when.

Cómo escribir condiciones más complejas en una sentencia when

Hasta ahora, aprendiste a escribir condiciones when para una sola condición equitativa, como cuando se le asigna un valor "Yellow" a la variable trafficLightColor. A continuación, aprenderás a usar la coma (,), la palabra clave in y la palabra clave is para formar condiciones when más complejas.

Crea un programa que determine si un número entre 1 y 10 es un número primo:

  1. Abre el Playground de Kotlin en otra ventana.

Regresarás al programa del semáforo más tarde.

  1. Define una variable x y, luego, asígnale un valor 3:
fun main() {
    val x = 3
}
  1. Agrega una sentencia when que incluya varias ramas para las condiciones 2, 3, 5 y 7, y sigue cada una con un cuerpo println("x is prime number between 1 and 10."):
fun main() {
    val x = 3

    when (x) {
        2 -> println("x is a prime number between 1 and 10.")
        3 -> println("x is a prime number between 1 and 10.")
        5 -> println("x is a prime number between 1 and 10.")
        7 -> println("x is a prime number between 1 and 10.")
    }
}
  1. Agrega una rama else con un cuerpo println("x is not prime number between 1 and 10."):
fun main() {
    val x = 3

    when (x) {
        2 -> println("x is a prime number between 1 and 10.")
        3 -> println("x is a prime number between 1 and 10.")
        5 -> println("x is a prime number between 1 and 10.")
        7 -> println("x is a prime number between 1 and 10.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Ejecuta el programa y, luego, verifica que el resultado sea el esperado:
x is a prime number between 1 and 10.

Cómo usar una coma (,) para varias condiciones

El programa de números primos contiene muchas sentencias println() repetidas. Cuando escribes una sentencia when, puedes usar una coma (,) para indicar que varias condiciones corresponden al mismo cuerpo.

Diagrama en el que se muestra la anatomía de una sentencia when. Comienza con una palabra clave when seguida de paréntesis con un bloque de parámetro dentro de ellos. A continuación, dentro de un par de llaves, hay dos líneas de casos. En la primera línea, hay un bloque de condición 1 seguido de una coma, seguido de un bloque de condición 2 seguido de un símbolo de flecha y un bloque de cuerpo. En la segunda línea, hay un bloque de condición seguido de un símbolo de flecha y un bloque de cuerpo.

En el diagrama anterior, si se cumple la primera o la segunda condición, se ejecuta el cuerpo correspondiente.

Vuelve a escribir el programa de números primos con este concepto:

  1. En la rama para la condición 2, agrega 3, 5 y 7 separados por comas (,):
fun main() {
    val x = 3

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        3 -> println("x is a prime number between 1 and 10.")
        5 -> println("x is a prime number between 1 and 10.")
        7 -> println("x is a prime number between 1 and 10.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Quita las ramas individuales de las condiciones 3, 5 y 7:
fun main() {
    val x = 3

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Ejecuta el programa y, luego, verifica que el resultado sea el esperado:
x is a prime number between 1 and 10.

Cómo usar la palabra clave in para un rango de condiciones

Además de la coma (,) para indicar varias condiciones, también puedes usar la palabra clave in y un rango de valores en las ramas when.

Diagrama en el que se muestra la anatomía de una sentencia when. Comienza con una palabra clave when seguida de paréntesis con un bloque de parámetro dentro de ellos. A continuación, dentro de un par de llaves, hay dos líneas de casos. En la primera línea, hay una palabra clave seguida de un bloque de inicio de rango, dos puntos, un bloque de fin de rango, un símbolo de flecha y, luego, un bloque de cuerpo. En la segunda línea, hay un bloque de condición seguido de un símbolo de flecha y un bloque de cuerpo.

Para usar un rango de valores, agrega un número que represente el inicio del rango seguido de dos puntos sin espacios y luego ciérralo con otro número que represente el final del rango.

Cuando el valor del parámetro es igual a cualquier valor en el rango entre el inicio del rango y el final del rango, se ejecuta el primer cuerpo.

En tu programa de números primos, ¿puedes imprimir un mensaje si el número está entre 1 y 10, pero no es un número primo?

Agrega otra rama con la palabra clave in:

  1. Después de la primera rama de la sentencia when, agrega una segunda rama con la palabra clave in seguida de un rango 1..10 y un cuerpo println("x is a number between 1 and 10, but not a prime number."):
fun main() {
    val x = 3

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Cambia la variable x por un valor 4:
fun main() {
    val x = 4

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Ejecuta el programa y, luego, verifica el resultado:
x is a number between 1 and 10, but not a prime number.

El programa imprime el mensaje de la segunda rama, pero no el mensaje de la primera ni la tercera rama.

Un diagrama que anota la sentencia when La línea 2,3,5,7 -> println("x is a prime number between 1 and 10.") se anota como caso 1. La línea in 1..10 -> println("x is a number between 1 and 10, but not a prime number.") se anota como caso 2. La línea else -> println("x isn't a prime number between 1 and 10.") se anota como caso 3.

El programa funciona de la siguiente manera:

  • A la variable x se le asigna un valor 4.
  • En el programa, se evalúan las condiciones de la primera rama. El valor 4 no es 2, 3, 5 ni 7, por lo que el programa omite la ejecución del cuerpo de la primera rama y continúa con la segunda. rama.
  • El valor 4 está entre 1 y 10, por lo que se imprime el mensaje del cuerpo x is a number between 1 and 10, but not a prime number..
  • Se ejecuta un cuerpo, por lo que el programa sale de la sentencia when e ignora la rama else.

Cómo usar la palabra clave is para verificar el tipo de datos

Puedes usar la palabra clave is como condición para verificar el tipo de datos de un valor evaluado.

Diagrama en el que se muestra la anatomía de una sentencia when. Comienza con una palabra clave when seguida de paréntesis con un bloque de parámetro dentro de ellos. A continuación, dentro de un par de llaves, hay dos líneas de casos. En la primera línea, hay una palabra clave seguida de un tipo, un símbolo de flecha y, luego, un cuerpo. En la segunda línea, hay una condición seguida de un símbolo de flecha y, luego, un cuerpo.

En el diagrama anterior, si el valor del argumento es del tipo de datos indicado, se ejecuta el primer cuerpo.

En tu programa con números primos, ¿puedes imprimir un mensaje si la entrada es un número fuera del rango de 1 a 10?

Agrega otra rama con la palabra clave is:

  1. Modifica x para que sea del tipo Any. Esto indica que x puede tener otro valor de tipo Int.
fun main() {
    val x: Any = 4

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. Después de la segunda rama de la sentencia when, agrega la palabra clave is y un tipo de datos Int con un cuerpo println("x is an integer number, but not between 1 and 10."):
fun main() {
    val x: Any = 4

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        is Int -> println("x is an integer number, but not between 1 and 10.")
        else -> println("x isn't a prime number between 1 and 10.")
    }
}
  1. En la rama else, cambia el cuerpo a println("x isn't an integer number."):
fun main() {
    val x: Any = 4

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        is Int -> println("x is an integer number, but not between 1 and 10.")
        else -> println("x isn't an integer number.")
    }
}
  1. Cambia la variable x por un valor 20:
fun main() {
    val x: Any = 20

    when (x) {
        2, 3, 5, 7 -> println("x is a prime number between 1 and 10.")
        in 1..10 -> println("x is a number between 1 and 10, but not a prime number.")
        is Int -> println("x is an integer number, but not between 1 and 10.")
        else -> println("x isn't an integer number.")
    }
}
  1. Ejecuta el programa y, luego, verifica el resultado:
x is an integer number, but not between 1 and 10.

El programa imprime el mensaje de la tercera rama, pero no los mensajes de la primera, segunda o cuarta rama.

Un diagrama que anota la sentencia when La línea 2,3,5,7 -> println("x is a prime number between 1 and 10.") se anota como caso 1. La línea in 1..10 -> println("x is a number between 1 and 10, but not a prime number.") se anota como caso 2. La línea Int -> println("x es un número entero, pero no entre 1 y 10"). La línea se anota como caso 3. La línea else > println("x no es un número entero"). La línea se anota como caso 4.

El programa funciona así:

  • A la variable x se le asigna un valor 20.
  • En el programa, se evalúan las condiciones de la primera rama. El valor 20 no es 2, 3, 5 ni 7, por lo que el programa omite la ejecución del cuerpo de la primera rama y continúa con la segunda. rama.
  • El valor 20 no está dentro del rango 1 a 10, por lo que el programa omite la ejecución del cuerpo de la segunda rama y pasa a la tercera rama.
  • El valor 20 es de tipo Int, por lo que se imprime el cuerpo x is an integer number, but not between 1 and 10.
  • Se ejecuta un cuerpo, por lo que el programa sale de la sentencia when e ignora la rama else.

Ponlo a prueba

Ahora, practica lo que aprendiste en tu programa semáforo.

Imagina que en algunos países hay un semáforo de color ámbar que advierte a los conductores de la misma manera que un semáforo en amarillo en otros países. ¿Puedes modificar el programa para que cubra esta condición adicional y mantenga las originales?

Cómo agregar una condición adicional con el mismo cuerpo

Agrega una condición adicional al programa de semáforo:

  1. Si todavía la tienes abierta, vuelve a la instancia del Playground de Kotlin con tu programa de semáforo.
  2. Si la cerraste, abre una nueva instancia de Playground de Kotlin y, luego, ingresa este código:
fun main() {
    val trafficLightColor = "Yellow"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}
  1. En la segunda rama de la sentencia when, agrega una coma después de la condición "Yellow" y, luego, una condición "Amber":
fun main() {
    val trafficLightColor = "Yellow"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow", "Amber" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}
  1. Cambia la variable trafficLightColor por un valor "Amber":
fun main() {
    val trafficLightColor = "Amber"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow", "Amber" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}
  1. Ejecuta este programa y, luego, verifica el resultado:
Slow

4. Cómo usar if/else y when como expresiones

Aprendiste a usar if/else y when como sentencias. Cuando usas condicionales como sentencias, permites que cada rama ejecute diferentes acciones en el cuerpo en función de las condiciones.

También puedes usar condicionales como expresiones a fin de mostrar valores diferentes para cada rama de condición. Cuando el cuerpo de cada rama sea similar, puedes usar expresiones condicionales para mejorar la legibilidad del código en comparación con las sentencias condicionales.

Un diagrama que describe una expresión if/else con la palabra clave val seguida de un bloque de nombre, un símbolo igual, una palabra clave if, un paréntesis con una condición dentro de ellos, un par de llaves con un bloque 1 en su interior, una palabra clave else y luego un par de llaves con un bloque de cuerpo dentro.

La sintaxis de los condicionales como expresiones es similar a las de las sentencias, pero la última línea de cuerpos de cada rama debe mostrar un valor o una expresión, y los condicionales se asignan a una variable.

Si los cuerpos solo contienen una expresión o un valor de retorno, puedes quitar las llaves para que el código sea más conciso.

Un diagrama que describe una expresión if/else con la palabra clave val seguida de un bloque de nombre, un símbolo igual, una palabra clave if, un paréntesis con una condición adentro, un bloque de expresión 1, una palabra clave else y, luego, un bloque de expresión 2.

En la siguiente sección, verás las expresiones if/else a través del programa de semáforo.

Cómo convertir una sentencia if en una expresión

Hay muchas repeticiones de la sentencia println() en esta sentencia if/else:

fun main() {
    val trafficLightColor = "Black"

    if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else if (trafficLightColor == "Green") {
        println("Go")
    } else {
        println("Invalid traffic-light color")
    }

}

Convierte esta sentencia if/else en una expresión if/else y quita esta repetición:

  1. En el Playground de Kotlin, ingresa al programa de semáforo anterior.
  2. Define una variable message y, luego, asígnale una sentencia if/else:
fun main() {
    val trafficLightColor = "Black"

    val message = if (trafficLightColor == "Red") {
        println("Stop")
    } else if (trafficLightColor == "Yellow") {
        println("Slow")
    } else if (trafficLightColor == "Green") {
        println("Go")
    } else {
        println("Invalid traffic-light color")
    }

}
  1. Quita todas las sentencias println() y sus llaves, pero deja los valores dentro de ellas:
fun main() {
    val trafficLightColor = "Black"

    val message =
      if (trafficLightColor == "Red") "Stop"
      else if (trafficLightColor == "Yellow") "Slow"
      else if (trafficLightColor == "Green") "Go"
      else "Invalid traffic-light color"
}
  1. Agrega una sentencia println() al final del programa y pasa la variable message como argumento:
fun main() {
    val trafficLightColor = "Black"

    val message =
      if (trafficLightColor == "Red") "Stop"
      else if (trafficLightColor == "Yellow") "Slow"
      else if (trafficLightColor == "Green") "Go"
      else "Invalid traffic-light color"

    println(message)
}
  1. Ejecuta este programa y, luego, visualiza el resultado:
Invalid traffic-light color

Ponlo a prueba

Convierte el programa de semáforo para que use una expresión when en lugar de una sentencia when:

  1. En el Playground de Kotlin, ingresa el siguiente código:
fun main() {
    val trafficLightColor = "Amber"

    when (trafficLightColor) {
        "Red" -> println("Stop")
        "Yellow", "Amber" -> println("Slow")
        "Green" -> println("Go")
        else -> println("Invalid traffic-light color")
    }
}

¿Puedes convertir la sentencia when en una expresión para no repetir las sentencias println()?

  1. Crea una variable message y asígnala a la expresión when:
fun main() {
    val trafficLightColor = "Amber"

    val message = when(trafficLightColor) {
        "Red" -> "Stop"
        "Yellow", "Amber" -> "Proceed with caution."
        "Green" -> "Go"
        else -> "Invalid traffic-light color"
    }
}
  1. Agrega una sentencia println() como la última línea del programa y, luego, pasa la variable message como argumento:
fun main() {
    val trafficLightColor = "Amber"

    val message = when(trafficLightColor) {
        "Red" -> "Stop"
        "Yellow", "Amber" -> "Proceed with caution."
        "Green" -> "Go"
        else -> "Invalid traffic-light color"
    }
    println(message)
}

5. Conclusión

¡Felicitaciones! Aprendiste sobre condicionales y cómo escribirlos en Kotlin.

Resumen

  • En Kotlin, la ramificación se puede lograr con condicionales if/else o when.
  • El cuerpo de una rama if en un condicional if/else solo se ejecuta cuando la expresión booleana dentro de la condición de rama if muestra un valor true.
  • Las ramas else if posteriores en un condicional if/else solo se ejecutan cuando las ramas if oelse if anteriores muestran valores false.
  • La rama else final en un condicional if/else solo se ejecuta cuando todas las ramas if o else if anteriores muestran valores false.
  • Se recomienda usar el condicional when para reemplazar un condicional if/else cuando hay más de dos ramas.
  • Puedes escribir condiciones más complejas en condicionales when con la coma (,), los rangos in y la palabra clave is.
  • Los condicionales if/else y when pueden funcionar como sentencias o expresiones.

Más información