Como passar um arrayList para o Callable é possível?
Você está vendo a versão anterior da nova experiência da Alura que estamos preparando para você. Em breve, ela ganha uma identidade visual novinha totalmente pensada em potencializar seus estudos!
Como passar um arrayList para o Callable é possível?
Fala Thiago, tudo bem ?
Não é possível passar um ArrayList para um Callable. Por padrão o método call() não recebe argumentos. Mas da pra tentar contornar de algumas formas.
Veja o exemplo onde podemos na implementação do Callable (mesmo não recebendo como parâmetro) acessar o contexto de uma lista e processar dados. No código o callable, dada uma lista original de pessoas, devolve uma lista de Strings com o primeiro nome das pessoas.
package threads;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.stream.Collectors;
public class Exemplo {
public static void main(String[] args) {
List<Person> people = Arrays.asList(
new Person("Rafael", "Rollo"),
new Person("Thiago", "Mileo"));
// inferindo pra implementação do Callable com lambda
Callable<List<String>> task = () -> {
// exibindo nome da thread que está atendendo (fora da main thread)
System.out.println(Thread.currentThread().getName());
// fazendo algo com a lista
return people.stream()
.map(p -> p.getFirstName())
.collect(Collectors.toList());
};
// solicitando inicio da execução
ExecutorService executorService = Executors.newSingleThreadExecutor();
Future<List<String>> names = executorService.submit(task);
try {
// pegando resultados que o callable devolve
names.get().forEach(System.out::println);
} catch (InterruptedException | ExecutionException e) {
throw new RuntimeException("Não foi possível processar em paralelo");
}
}
}
class Person {
private String firstName;
private String lastName;
public Person(String firstName, String lastName) {
this.firstName = firstName;
this.lastName = lastName;
}
// getFirstName() omitido
// getLastName() omitido
}
Aqui processamos em paralelo com a implementação do Callable (inferida a partir de uma lambda expression do java 8) que consegue acesso ao contexto da lista e ao final consumimos a Future retornada por ele pra acessar a lista resultante.
Você poderia ter uma método em uma classe ou serviço que recebe o arraylist (não o call() do Callable) e na sua implementação fazer algo parecido. Essa classe seria responsável por inferir para a implementação do Callable usando essa lista.
Existem só alguns cuidados. Perceba que apenas consumimos a lista no Callable, pois ela deve ser efetivamente final, ou seja, não podemos alterar sua referência. Em geral usaria maps, filters, reduces tudo que use a lista original e origine listas resultantes sem alterar o estado da original.
Acho que você poderia pensar em algo assim. Espero ter ajudado no pensamento. Abraço!