Expresiones Lambda en java 8 - Magia básica

Una EXPRESIÓN LAMBDA se parece mucho a la declaración e implementación de un método, así que podemos considerar las expresiones LAMBDA como métodos anónimos o métodos sin un nombre.

 

Una expresión lambda tiene las siguientes características:

1. Un listado de parámetros separados por una coma y encerrados en paréntesis:

   a) Puedes omitir el tipo de dato de cada parámetro.

   b) Si solo hay 1 parámetro también puedes omitir el uso de los paréntesis.

   La expresión: p -> p.getNombrePersona() es correcta; también puedes utilizarla de esta forma: (Persona p) -> p.getNombrePersona()

2. El token de flecha que está compuesto por un guión y el signo de mayor que: ->

3. El cuerpo de la expresión que básicamente es la implementación del método que se quiere ejecutar; puede ser una sentencia simple o un bloque encerrado en {} .

   Si utilizas una sentencia simple puedes omitir la palabra "return" y el runtime de java evalúa la expresión y devuelve el resultado.

 

IMPORTANTE: Te puedes descargar el código directamente del repositorio en github o en formato zip.

 

Ejemplos de expresiones lambda:

1. Código java de una interfaz con únicamente 1 método que no recibe parámetros y no devuelve nada (void):

/**
* Código generado por Gerado Pucheta Figueroa
* Twitter: @ledzedev
* http://ledze.mx
* 11/03/2017.
*/
public interface MiPrimerLambda {

void metodoSinParametros();
}

 

2. Código java de una interfaz con únicamente 1 método que recibe 2 parámetros int y devuelve otro int.

/**
* Código generado por Gerado Pucheta Figueroa
* Twitter: @ledzedev
* http://ledze.mx
* 11/03/2017.
*/
public interface OperacionBasicaLambda {

int operacion(int a, int b);
}

3. Código java de una clase que utiliza de distintas formas las interfaces primero con implementaciones antiguas y luego utilizando expresiones lamda.

public static void main(String[] args) {

//Iniciamos con una interfaz cuyo único método no devuelve nada y no tiene parámetros
//la implementación es anónima simulando un lambda.
MiPrimerLambda miPrimerLambdaDeclaracionAnonima = new MiPrimerLambda() {

@Override
public void metodoSinParametros() {

System.out.println("Hola mundo ledze con declaración anónima.");
}
};
miPrimerLambdaDeclaracionAnonima.metodoSinParametros();
System.out.println("/***********************************/");

//Ahora el mismo método es implementado con el paradigma de los lambdas.
MiPrimerLambda miPrimerLambda = () -> System.out.println("Hola mundo ledze con lambdas.");

miPrimerLambda.metodoSinParametros();

System.out.println("/***********************************/");

//Aquí tenemos 4 objetos del mismo tipo con diferente implementación.
OperacionBasicaLambda opSuma = (a,b) -> a+b;

OperacionBasicaLambda opResta = (a,b) -> a-b;
OperacionBasicaLambda opMultiplica = (a,b) -> a*b;
OperacionBasicaLambda opDivide = (a,b) -> (int)(a/b);

int resultadoSuma = opSuma.operacion(5,5);
int resultadoResta = opResta.operacion(5,5);
int resultadoMultiplica = opMultiplica.operacion(5,5);
int resultadoDivide = opDivide.operacion(5,5);

System.out.println("Lambda ledze: Misma clase, distinto objeto diferente implementación. Resultado suma = "+resultadoSuma);
System.out.println("Lambda ledze: Misma clase, distinto objeto diferente implementación. Resultado resta = "+resultadoResta);
System.out.println("Lambda ledze: Misma clase, distinto objeto diferente implementación. Resultado multiplicación = "+resultadoMultiplica);
System.out.println("Lambda ledze: Misma clase, distinto objeto diferente implementación. Resultado división = "+resultadoDivide);
System.out.println("/***********************************/");

//También puedes sobre-escribir el método para que se ejecute tu implementación.
OperacionBasicaLambda opGenerica;


opGenerica = (a,b) -> a+b;
System.out.println("Lambda ledze: Mismo objeto con diferente implementación. Resultado = "+opGenerica.operacion(10,2));
opGenerica = (a,b) -> a-b;
System.out.println("Lambda ledze: Mismo objeto con diferente implementación. Resultado = "+opGenerica.operacion(10,2));
opGenerica = (a,b) -> a*b;
System.out.println("Lambda ledze: Mismo objeto con diferente implementación. Resultado = "+opGenerica.operacion(10,2));
opGenerica = (a,b) -> a/b;
System.out.println("Lambda ledze: Mismo objeto con diferente implementación. Resultado = "+opGenerica.operacion(10,2));
}

Concluyendo

Podemos ver claramente que las expresiones lambda nos facilitan la vida para realizar implementaciones independientes y para evitar el uso de clases anónimas en nuestro código fuente.

Como ya lo mencioné, podemos considerar las expresiones LAMBDA como métodos anónimos o métodos sin un nombre.

El resultaddo de ejecutar el código expuesto es el siguiente.

 

 

Add a comment

Java 8 : API procesamiento JSON-P en streaming

JSON-P Streaming

 

1. Configuración MAVEN.

 

<modelVersion>4.0.0</modelVersion>

<groupId>com.ledzedev.ejemplosjson</groupId>
<artifactId>ledzedev</artifactId>
<version>1.0-SNAPSHOT</version>

<name>ledzedev</name>

<dependencies>
<dependency>
<groupId>javax.json</groupId>
<artifactId>javax.json-api</artifactId>
<version>1.0</version>
</dependency>
<dependency>
<groupId>org.glassfish</groupId>
<artifactId>javax.json</artifactId>
<version>1.0.4</version>
</dependency>

<!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-api -->
<dependency>

<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.21</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-simple -->
<dependency>

<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>1.7.21</version>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>2.5.1</version>
<configuration>
<!-- o cualquier versión que ocupes, en mi caso java 8 -->
<source>1.8</source>

<target>1.8</target>
</configuration>
</plugin>
</plugins>
</build>

 

2. Archivo JSON (Generado aleatoriamente con json-generator y guardado en un archivo propio).

Este archivo se encuentra en el directorio resources dentro del proyecto.

 

3. Java (JSON-P Streaming).

 

package com.ledzedev.ejemplosjson;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.json.Json;
import javax.json.stream.JsonParser;
import java.io.IOException;
import java.io.InputStream;

/**
* Código generado por Gerado Pucheta Figueroa
* Twitter: @ledzedev
* 27/Oct/2016.
*/
public class ProcesaPaisesJsonStream {


private static final Logger log = LoggerFactory.getLogger(ProcesaPaisesJsonStream.class);

public static void main(String[] args) {
String paisABuscar = "Alaska";
String emailDelPais = ProcesaPaisesJsonStream.obtenerEmailConPais(paisABuscar);

log.info("El e-mail de la dirección ubicada en " + paisABuscar + ", es: " + emailDelPais);
}

public static String obtenerEmailConPais(String pais) {

JsonParser jsonParser = null;
String email = null;

//paso 1. Obtener el JSON, en este caso viene de un archivo, pero puede venir de un servicio en web.
/* Ejemplo si viene por web
URL url = new URL("http://restcountries.eu/rest/v1/all");
InputStream inputStream = url.openStream();
*/
try (InputStream inputStream = EjemploPaisesJson.class.getClassLoader().getResourceAsStream("json-generator-file.json")) {

jsonParser = Json.createParser(inputStream);

//paso 2. recorrer el JSON hasta que se procese|encuentre lo que se necesite.
boolean paisEncontrado = false;


while (jsonParser.hasNext() && !paisEncontrado) {

JsonParser.Event event = jsonParser.next();
if (event.equals(JsonParser.Event.KEY_NAME)) {

switch (jsonParser.getString()) {
//Nota: debido a que el api solo recorre hacia adelante y en el archivo el campo email está antes que el campo address,
// tenemos que guardar el valor de email, previo a que se valide el contenido de address.
case "email":

//guardamos el valor de email
jsonParser.next();

email = jsonParser.getString();
break;
case "address":
jsonParser.next();
String direccion = jsonParser.getString();
//si el pais que buscamos se encuentra en address entonces mandamos la variable paisEncontrado a true
paisEncontrado = (direccion != null && direccion.contains(pais));

break;
}
}
}
} catch (IOException e) {
log.error("error al leer el archivo json", e);
return null;
}
return email;
}
}

4. Descárgate el código en github o en zip y haz pruebas.

Artículo relacionado.
-
Java 8 : API para procesamiento JSON-P
Add a comment

Read more: Java 8 : API procesamiento JSON-P en streaming

Java 8 : API para procesamiento JSON-P

 

JSON-P

Sabemos que JSON-P no es la primer API para procesamiento de información en formato JSON, pero si es la primera que ha sido estandarizada a través del Java Community Process (JCP por sus siglas en inglés).

 

1. Configuración Maven.

Agregamos a nuestro pom.xml, las 2 APIs que necesitamos para JSON-P (javax.json como api principal y javax.json de glassfish) y como complemento ocupamos las 2 librerías de slf4j como fachada para tener un logger estándar y evitar el System.out.println()

<groupId>com.ledzedev.ejemplosjson</groupId>
<artifactId>ledzedev</artifactId>
<version>1.0-SNAPSHOT</version>

<name>ledzedev</name>

<dependencies>
<dependency>
<groupId>javax.json</groupId>
<artifactId>javax.json-api</artifactId>
<version>1.0</version>
</dependency>
<dependency>
<groupId>org.glassfish</groupId>
<artifactId>javax.json</artifactId>
<version>1.0.4</version>
</dependency>

<!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-api -->
<dependency>

<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.21</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.slf4j/slf4j-simple -->
<dependency>

<groupId>org.slf4j</groupId>
<artifactId>slf4j-simple</artifactId>
<version>1.7.21</version>
</dependency>
</dependencies>

 

2. Archivo JSON.

[
{
"pais": "Colombia",
"poblacion": 48747632,
"idiomasOficiales": [
{
"idioma": "Español"
},

{
"idioma": "Inglés"
}

]
},
{
"pais": "México",
"poblacion": 120000000,
"idiomasOficiales": [
{
"idioma": "Español"
},

{
"idioma": "Maya"
},

{
"idioma": "Espanglish"
}

]
}
]

3. Java (JSON-P Object Model API).

 

package com.ledzedev.ejemplosjson;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.json.Json;
import javax.json.JsonArray;
import javax.json.JsonObject;
import javax.json.JsonReader;
import javax.json.JsonValue;
import java.io.FileNotFoundException;
import java.io.InputStream;
import java.util.List;
import java.util.stream.Collectors;

/**
*
* Código generado por Gerardo Pucheta Figueroa
* Twitter: @ledzedev
* 19/Oct/2016
*
*/
public class EjemploPaisesJson {


private final Logger log = LoggerFactory.getLogger(EjemploPaisesJson.class);

public JsonArray getJsonArrayFromFile(String archivo) throws FileNotFoundException {
InputStream inputStream = EjemploPaisesJson.class.getClassLoader().getResourceAsStream(archivo);

JsonReader jsonReader = Json.createReader(inputStream);
JsonArray jsonArray = jsonReader.readArray();

return jsonArray;
}

public void consultaObjetoJson(String llave){
JsonArray jsonArray = null;
String nombreArchivo = "paises.json";
log.info("Leyendo {} llave: {}",nombreArchivo, llave);
try {
jsonArray = getJsonArrayFromFile(nombreArchivo);
} catch (FileNotFoundException e) {
log.error("ARCHIVO NO ENCONTRADO.",e);
return;
}

List<JsonObject> lst = jsonArray.getValuesAs(JsonObject.class);

lst.forEach(jsonObject -> {
JsonValue jsonValue = jsonObject.get(llave);
switch (jsonValue.getValueType()) {
case STRING:
log.info("capital: " + jsonObject.getString(llave, "Llave desconocida!!!"));
break;
case ARRAY:
JsonArray array = jsonObject.getJsonArray("idiomasOficiales");
String idiomas = array.getValuesAs(JsonObject.class)
.stream()
.map(lang -> lang.getString("idioma", ""))
.collect(Collectors.joining(", "));
log.info("idiomas: " + idiomas);
break;
case NUMBER:
log.info("población: " + jsonObject.getInt("poblacion"));
break;
}
});
}

public static void main(String [] args){

EjemploPaisesJson ejemploPaisesJson = new EjemploPaisesJson();

ejemploPaisesJson.consultaObjetoJson("pais");
ejemploPaisesJson.consultaObjetoJson("poblacion");
ejemploPaisesJson.consultaObjetoJson("idiomasOficiales");

}

}
 
Descargar de github
Descargar en zip


Add a comment

Subcategories