segunda-feira, 21 de agosto de 2017

Nashorn: Javascript sobre a JVM

Programar em Java está cada vez mais rápido e simples, desde as mudanças que começaram a surgir na versão 7 do Java, a verbosidade característica da linguagem foi reduzindo e agora no Java 8 alcançamos um nível muito superior com a programação funcional presente na linguagem.

Porém, muitos ainda dizem que estas funcionalidades chegaram um pouco atrasadas na linguagem, e durante este tempo que ainda não tinhamos a programação funcional presente no Java, foram surgindo outras linguagens sobre a JVM que visavam trazer novos paradigmas para os programadores.

Como estamos acompanhando, o Javascript tem tomado cada vez mais conta dos projetos de desenvolvimento mudo afora, principalmente agora ele roda firme e forte no lado do servidor, através de diversos projetos diferentes, sendo a referência maior o Node.js, com isto, novamente o Javascript ganhou o foco, principalmente após a criação da instrução invokedynamic, que permitiu a criação e invocação de métodos durante a execução do programa.

Assim, a comunidade iniciou um novo projeto, o Nashorn, que permite executar Javascript na JVM, dentro de outros programas em Java e também executar Java dentro de Javascript. Pode parecer loucura, mas é muito simples iniciar o desenvolvimento, como vemos abaixo.

A primeira coisa que notamos, é que além de rodar scripts, foi criado um interpretador interativo, onde você digita os comandos e recebe o resultado na hora, similar aos já existentes em Python e Ruby. Para acessa-lo basta digitar o comando jrunscript:



Note que alguns comandos já executam normalmente, como o print, criação de variáveis e também operações aritméticas. Porém, não temos apenas o interpretador interativo, podemos executar diretamente scripts, bastando colocar no prompt jrunscript seuarquivo.js, vejamos um exemplo:


Este script simples apenas imprime alguns números na tela, porém já podemos ver como diversos elementos do Javascript atuam em execução, sendo a saída:


Mas não se limita apenas a operadores básicos da linguagem, como o script roda sobre a máquina virtual Java, ou seja, ele é convertido em bytecodes, também podemos invocar bytecodes já existentes, ou seja, invocar classes presentes na linguagem Java, como este exemplo que invoca a classe FileReader e Scanner, lendo e exibindo as linhas de um arquivo:


Perceba como escrevemos muito pouco código para realizar tarefas interessantes, tudo isso através de uma linguagem familiar e simples, porém com muitos recursos em sua sintaxe.

sábado, 16 de julho de 2016

Iterando sobre uma matriz com um único loop

Quando estamos nas aulas iniciais de programação, aprendemos a iterar sobre vetores e matrizes, sendo que no segundo caso é necessário criar um loop (for, while e etc) para cada dimensão de nossa matriz. Desta forma criamos muitas vezes um código com vários níveis de aninhamento no nosso código.

Uma outra forma de lidar com isto é criando uma forma de a partir de um único índice extrair o valores dos sub-índices, uma tarefa simples se utilizarmos módulo.

domingo, 18 de maio de 2014

Encurtando links em Java usando o Migre.me

Uma pequena forma de como usar o Migre.me dentro de sua aplicação para encurtar URLs. A requisição é feita utilizando alguns componentes da especificação JAX-RS, utilizando o Jersey como implementação.

Para fazer parser do JSON recebido, utilizamos o Jackson, o que deixa as coisas muito simples.

domingo, 16 de março de 2014

Dando um close no Java 7: AutoCloseable

Gerenciar recursos sempre foi algo muito chato, principalmente quando parte do ciclo de vida do objeto é fecha-lo, senão você poderá ter problemas na execução do seu programa. Vamos por exemplo analisar um código que abre um arquivo e itera sobre ele exibindo seu conteúdo linha a linha:
        FileReader readerAntigo = null;
        try {
            readerAntigo = new FileReader("arquivo.txt");
            Scanner scanner = new Scanner(readerAntigo);

        while(scanner.hasNext()) {
            System.out.println(scanner.next());
        }
        } catch (FileNotFoundException e ) {
            System.out.println("Arquivo não encontrado");
        } finally {
            try {
                readerAntigo.close();
            } catch (IOException e) {
                System.out.println("Erro ao fechar o arquivo");
            }
        }
Perceba como é chato gerenciar o arquivo, para que eu possa abrir e fechar são necessário duas capturas de sessão, sem contar que ainda é necessário que o programador lembre-se de fechar o arquivo, algo que não pode ser tão crítico, mas se imaginarmos conexões JDBC, logo o banco começará a recusar conexões pois esquecemos de fecha-las anteriormente.

Para ajudar a solucionar isso, no Java 7 foi introduzi o AutoCloseable, que permite que recursos existam apenas dentro de um bloco e ao seu final (ou caso seja lançado uma exceção) sejam fechados devidamente. Para isso, foi criada a interface AutoCloseable, e o a classe que a implementada de sobrescrever o método close(). Ao abrir um novo recurso, você deve declara-lo e instancia-lo dentro de parentes após o try, ficando assim:

quinta-feira, 6 de março de 2014

Mapeando e Reduzindo - Java 8

As vezes precisamos processar dados em um volume maior, onde é necessário filtrar a informação, selecionar ou alterar o que queremos para depois realizar o processamento. Como exemplo, vamos imaginar uma lista de alunos, onde cada instância tem seu nome e nota. Desta lista queremos a média geral, a média dos alunos aprovados (ou seja, quem tirou nota seis ou mais) e a média dos reprovados (nota menor que seis). Para isso, vamos primeiro visualizar nossa lista:

        List<Aluno>alunos = new ArrayList<>();

        Aluno aluno1 = new Aluno("Cebolinha", 8.0);
        Aluno aluno2 = new Aluno("Cascao", 6.5);
        Aluno aluno3 = new Aluno("Monica", 9.0);
        Aluno aluno4 = new Aluno("Magali", 3.0);

        alunos.addAll(Arrays.asList(aluno1, aluno2, aluno3, aluno4));

Apesar da simplicidade dos nossos dados, para poder separar a nossa lista de forma a realizar esta média, precisamos iterar sobre todos os seus elementos. Vamos fazer primeiro a média mais simples, sem nenhum critério:

        Double media = new Double("0");
        int quantidadeDeAlunos = 0;

        for (Aluno aluno : alunos) {
            media = Double.sum(media, aluno.getNota());
            quantidadeDeAlunos++;
        }

        System.out.println(media / quantidadeDeAlunos);

domingo, 2 de março de 2014

Filtrando resultados (Predicados) - Java 8

Muitas vezes precisamos filtrar listas, listas de todos os tipos, desde números básicos, passando por Strings, até tipos complexos. Abaixo temos um exemplo simples disto, onde temos uma lista com alguns nomes e queremos filtra-la e exibi-la para o usuário (no caso, todos os nomes que tiverem a letra "u" serão exibidos):

        List<string> nomes = new ArrayList<>();

        nomes.add("João da Silva");
        nomes.add("Joaquim da Padaria");
        nomes.add("Lucas Polo");
        nomes.add("Chaves");

        List<string> nomesFiltrados = new ArrayList<>();

        System.out.println("Iniciando filtragem");

        for (String nome : nomes) {
            System.out.println("Avaliando: " + nome);
            if (nome.contains("u")) nomesFiltrados.add(nome);
        }

        System.out.println("Iniciando impressão");

        for (String nome : nomesFiltrados) {
            System.out.println(nome);
        }
A saida é:
Iniciando filtragem
Avaliando: João da Silva
Avaliando: Joaquim da Padaria
Avaliando: Lucas Polo
Avaliando: Chaves
Iniciando impressão
Joaquim da Padaria
Lucas Polo
Repare que primeiros os resultados são filtrados e depois exibidos, mas variando com o tamanho da lista, pode demorar muito tempo para filtrarmos uma lista inteira, e por isso, muitas vezes, é melhor avaliar se o elemento passa no filtro e trata-lo devidamente, ganhando assim mais velocidade. Na programação funcional, temos um meio de lidar com isso, chamado avaliação preguiçosa.

Lembrando que métodos também pode ser passados como parâmetros, por isso, podemos armazena-los e utilizar suas funções posteriormente. Métodos que realizam a avaliação de elementos, são conhecidos como predicados, que no Java é representado pela classe Predicate e contem o método filter.

segunda-feira, 23 de setembro de 2013

Inversão de Controle e Injeção de Dependências

Quando comecei a programar na escola (curso técnico que fiz na época), comecei em uma das linguagens mais legais e, de certo modo, estranha que existe, a linguagem C. Alguns conceitos dela não são claros logo de inicio, pois não fazem nenhum paralelo com o mundo real. Um deles é o conceito de ponteiros e alocação de memória, onde você dinamicamente pode alocar memória para seu programa utilizar. Porém, como dizia o Tio Ben: "Grandes poderes trazem grandes responsabilidades", logo você se via obrigado a "lembrar" de liberar toda a memória alocada quando não fizesse mais uso dela, senão seu programa logo travaria junto com o seu sistema operacional.

O mundo mudou, os tempos agora são outros, temos a internet, o relógio digital e o Garbage Collector, que faz toda a gerência da coleta de memória que não é mais utilizada por nossos objetos. Porém agora temos que gerênciar outros recursos, como objetos que abrem arquivos e devem fecha-los ou conexões com o banco de dados. Caso você não os feche, seu arquivo não poderá ser aberto novamente ou seu banco de dados começará a recusar conexões, e sinceramente, isso é muito chato.