Entrada de Dados em Java

A leitura de dados, a partir de um programa em Java, pode ser feita de várias maneiras. Descreve-se, a seguir, como a efectuar directamente a partir do InputStream System.in ou usando um BufferedReader.

Directamente de System.in

System.in é um objecto que representa a entrada padrão de um programa em Java e está, normalmente, associado à entrada de dados através do teclado. (Em Linux, System.in pode ser associado a um ficheiro através do operador de redireccionamento da entrada "< ficheiro".) A sua classe é InputStream e possui, entre outros, o método int read() que permite ler um carácter.

A leitura de um inteiro é feita dígito a dígito, como é exemplificado pelo método seguinte.

  // Lê e devolve um inteiro, assumindo que os separadores
  // são espaços, que é chamado antes de ser lido qualquer
  // dígito e que o carácter que segue o número (espaço ou
  // fim de linha) pode ser desprezado.
  private static int leInteiro(InputStream entrada)
    throws IOException
  {
    int numero = 0;
    int c;

    // ignora os espaços antes do primeiro dígito
    while ((c = entrada.read()) == ' ')
      ;

    do {
      numero = numero * 10 + (c - '0');
      c = entrada.read();
    } while (Character.isDigit((char) c));

    return numero;
  }
Exemplo de uso:
    // se a linha contém dois inteiros seguidos
    int inteiro1 = leInteiro(System.in);
    int inteiro2 = leInteiro(System.in);

Para efeitos do trabalho de Estruturas de Dados, a leitura de uma String, depois de consumidos os espaços que a possam preceder, consiste num ciclo simples que lê todos os caracteres até ao fim da linha, seguido da construção da String com os caracteres lidos.

Usando um BufferedReader

Os objectos da classe BufferedReader são usados para a entrada de dados para um programa em Java. Estes objectos possuem um método String readLine() que permite ler uma linha de texto e a devolve numa String.

Para obter um BufferedReader associado à entrada padrão do programa, este deve incluir a instrução:

    BufferedReader entrada =
      new BufferedReader(new InputStreamReader(System.in));

Neste caso, a leitura de um inteiro será feita de uma String, a partir de uma determinada posição, e deverá devolver, além do valor lido, a posição do carácter a seguir ao último dígito do número, para que posteriormente possam ser extraídos dados da mesma linha sem reler os já obtidos. Este funcionamento é ilustrado no código que se segue.

  // Classe usada para devolver um inteiro lido de uma String
  // e o índice da posição a seguir ao último dígito do número.
  private static class intIndice {
    int numero;   // número lido
    int proximo;  // índice do próximo carácter

    intIndice(int num, int prox)
    {
      numero = num;
      proximo = prox;
    }
  }

  // Lê um inteiro da String `linha' a partir da posição
  // `inicio', assumindo espaços como separadores. Devolve
  // o número lido e a posição do carácter que se lhe segue.
  private static intIndice leInteiro(String linha, int inicio)
  {
    int numero = 0;
    int i = inicio;

    // ignora os espaços antes do primeiro dígito
    while (linha.charAt(i) == ' ')
      ++i;

    do {
      numero = numero * 10 + (linha.charAt(i) - '0');
      ++i;
    } while (i < linha.length() && Character.isDigit(linha.charAt(i)));

    return new intIndice(numero, i);
  }
Exemplo de uso:
    int inteiro1, inteiro2;
    intIndice ii;
    String linha = entrada.readLine();

    // se a linha contém dois inteiros seguidos
    ii = leInteiro(linha, 0);
    inteiro1 = ii.numero;
    ii = leInteiro(linha, ii.proximo);
    inteiro2 = ii.numero;

Um valor sob a forma de String é obtido directamente na String lida ou através do método String substring(int).

Nota

Todo o código apresentado nesta página assume o formato para os dados descrito no enunciado do trabalho.