y Kotlin) Creador del framework Open Source Hexagon Organizador de KotlinMAD Trabajando en azampar.co • Github: http://github.com/jaguililla • Twitter: http://twitter.com/jaguililla • Linkedin: http://linkedin.com/in/jaguililla
sus propias necesidades: • Mantener una gran cantidad de código Java en producción • En distintas plataformas (Web y Desktop principalmente) • Eliminar los problemas más comunes en sus productos. Ej: NPEs Diseñado para facilitar el desarrollo de herramientas (ya cuenta con un buen compilador y un REPL) Fue liberado como Open Source bajo licencia Apache 2 en Github La versión 1.0 se liberó en febrero de 2016
vale para todo) Compilado a Java bytecode y JavaScript Tipado estático (permite dinámico para JavaScript) Multiparadigma: OO y FP Se puede ejecutar sobre Android, Servidores, Escritorio, Navegador y Shell
(como Optional). Parte del lenguaje, no de la librería Any? es la base de todos los tipos (como Object en Java) Unit es el equivalente a void en Java Nothing es utilizado por expresiones que no retornan ningún valor
clase `com.paquete.De0a100Kt` package com.paquete // Puede estar en cualquier directorio import java.util.Date.parse as parseDate // Las definiciones pueden renombrarse // Definiciones `public` si no se indica `internal` o `private` val valPaquete = 0 // import com.paquete.valPaquete fun funPaquete() = true // En Java: com.paquete.De0a100Kt.funPaquete() // Ejecutado como `java com.paquete.De0a100Kt` fun main(args: Array<String>) { println("Hola Kotlin") }
sin tipos //constante = false // Error de compilación var variable: String = """cadenas multilínea con sustitución de variables $constante ${2 + 2}""" // Los operadores de bits son funciones infijas val bits = 0b1 shl 1 and 0b0 // Inicializado en el primer acceso val initEnAcceso: Long by lazy { System.currentTimeMillis() }
'?' Indica valor opcional //val error: Int = entero + 1 // Con `?:` Puedes controlar `null` de manera concisa val ok: Int = (entero ?: 0) + 1 data class Address(val street: String, val locality: String?) val address: Address? = Address("Atocha, 1", "Madrid") // Operador safe call `?.` val localidad = address?.locality ?: "Sin localidad"
= 0, parametro: String = "defecto") = parametro + entero.toString() funcion() // Argumentos por defecto funcion(parametro = "valor") // Paso de argumentos por nombre fun procedimiento(): Unit { println("Hola") } // Unit es opcional fun matroska() { val local = 1 fun matroska1() = local }
= { a: Int, b: Int -> "$a $b" } // Se invocan como una función lambda(10, 20) // Se pueden pasar por parámetro fun higherOrderFun(p: Int, lambda: (Int) -> Int) = lambda(p) // Si es el último parámetro acepta sintaxis alternativa higherOrderFun(10, { it * 2 }) higherOrderFun(10) { it * 2 }
Útiles para ampliar librerías sin código fuente fun String.addTimestamp() = this + " " + System.currentTimeMillis() // El objeto sobre el que se aplican se llama 'receiver' // Se puede especificar un `receiver` nullable fun String?.addNullTimestamp() = this ?: "Esto es null" + " " + System.currentTimeMillis() "hola".addTimestamp() null.addNullTimestamp()
pueden contener variables fun funcion(): String } abstract class ClaseAbstracta { abstract fun funcion(): String } // Las clases son ‘final’ por defecto // Los parámetros del constructor principal se definen en la clase open class ClaseBase(val campo: String = "foo")
Clase(param: String, val propiedad: Int = 0) : ClaseBase(param), Interfaz { var propiedad2 = param override val valor = 42 init { println(param) } constructor() : this("parametro", 99) fun metodo() = "resultado" override fun funcion() = "implementada" } val c = Clase("parametro") // No se utiliza 'new'
// Field es la variable final (p. reservada) class PersonV2 { var age: Int = 0 get() = field set(value) { require(value < 18) field = value } } // Compila con `PersonV1` y `PersonV2` val p = PersonV2() // Con `PersonV2` lanza una excepción p.age = 8
// Pueden implementar interfaces, no pueden heredar clases data class Person(val name: String, val age: Int = 0) val alfredo = Person("Alfredo Lambda", 61) // Copiar instancia cambiando campos val alfredoLanda = alfredo.copy( name = "Alfredo Landa", age = 62 )
(v) { is String -> println (v.substring(1..2)) in 1..9 -> println("Int") !in 1..9 -> println("Fuera de rango") 0 -> println ("Zero") else -> println ("Nada de lo anterior") } // Se puede utilizar como un if-elseif // más limpio when { (v as Int > 10) -> println("+10") "" is String -> println ("true") else -> println ("Nunca se ejecuta") }
Unido" to "UK" ) assert("España" in mapa) assert(mapa["España"] == "ES") val mapa2 = mapa + ("Italia" to "IT") val mapaM = mutableMapOf ("a" to 0, "b" to true) mapaM["a"] = 'C'
Wasabi, Kara, Hexagon Desktop (JavaFX) TornadoFX Testing: Spek, KotlinTest y Mockito-kotlin Inyección de dependencias: Kodein e Injekt Otros: Gradle (scripts con Kotlin en vez de Groovy) Es muy sencillo utilizar librerías escritas en Java
los acabes conocerás el lenguaje bastante bien Blog: últimas noticias del lenguaje Slack: muy activo (tiene un canal en español) Kotlin for Android: De Antonio Leiva Kotlin in Action: Manning (MEAP) Stack Overflow