Como lidar com entrada de usuário inválida em um programa Java

JavaBeginner
Pratique Agora

Introdução

O tratamento de entrada inválida do usuário é um aspecto crucial da programação Java que garante que suas aplicações permaneçam robustas e confiáveis. Quando os usuários interagem com seus programas, eles podem fornecer dados inesperados ou incorretos que poderiam causar a falha da sua aplicação se não forem gerenciados adequadamente.

Neste laboratório, você aprenderá como lidar efetivamente com entrada inválida do usuário em aplicações Java. Você explorará diferentes técnicas, desde a verificação básica de erros até métodos de validação mais avançados. Ao final deste laboratório, você será capaz de escrever programas Java que lidam graciosamente com erros do usuário e fornecem feedback apropriado.

Criando um Programa Java Básico com Entrada do Usuário

Neste primeiro passo, criaremos um programa Java simples que coleta a entrada do usuário. Isso servirá como base para aprender técnicas de validação de entrada.

Entendendo a Entrada do Usuário em Java

Java oferece várias maneiras de coletar entrada dos usuários. Para aplicações de console, a classe Scanner do pacote java.util é comumente usada. Esta classe oferece métodos para ler diferentes tipos de entrada, como inteiros, números de ponto flutuante e strings.

Criando o Programa de Entrada

Vamos começar criando um programa Java básico que solicita a idade de um usuário e a imprime de volta.

  1. Primeiro, abra o WebIDE e navegue até o diretório do projeto:

  2. Crie um novo arquivo clicando no ícone "New File" no explorador de arquivos do WebIDE. Nomeie o arquivo UserInputDemo.java

  3. Adicione o seguinte código ao arquivo:

import java.util.Scanner;

public class UserInputDemo {
    public static void main(String[] args) {
        // Create a Scanner object to read input
        Scanner scanner = new Scanner(System.in);

        // Prompt the user for their age
        System.out.print("Please enter your age: ");

        // Read the input
        int age = scanner.nextInt();

        // Display the entered age
        System.out.println("You entered: " + age);

        // Close the scanner
        scanner.close();
    }
}
  1. Salve o arquivo pressionando Ctrl+S ou selecionando "File" > "Save" no menu.

  2. Abra um terminal no WebIDE clicando em "Terminal" > "New Terminal" no menu superior.

Input Demo
  1. Compile o programa Java executando o seguinte comando:
javac UserInputDemo.java
  1. Execute o programa com:
java UserInputDemo
  1. Insira um número quando solicitado, por exemplo, 25. Você deverá ver a seguinte saída:
Please enter your age: 25
You entered: 25

O que Acontece com Entrada Inválida?

Agora, vamos ver o que acontece quando fornecemos entrada inválida. Execute o programa novamente:

java UserInputDemo

Desta vez, insira um valor não numérico, como twenty-five. Você verá uma mensagem de erro semelhante a:

Please enter your age: twenty-five
Exception in thread "main" java.util.InputMismatchException
 at java.base/java.util.Scanner.throwFor(Scanner.java:943)
 at java.base/java.util.Scanner.next(Scanner.java:1598)
 at java.base/java.util.Scanner.nextInt(Scanner.java:2263)
 at java.base/java.util.Scanner.nextInt(Scanner.java:2217)
 at UserInputDemo.main(UserInputDemo.java:12)

Esta InputMismatchException ocorre porque o programa esperava uma entrada numérica (um inteiro), mas recebeu texto em vez disso. O programa trava em vez de lidar com isso graciosamente. Nos próximos passos, aprenderemos como lidar com essas entradas inválidas corretamente.

Lidando com Exceções para Entrada Inválida

Neste passo, modificaremos nosso programa para lidar com entrada inválida usando o mecanismo de tratamento de exceções do Java.

Entendendo as Exceções Java

Exceções em Java são eventos que interrompem o fluxo normal da execução do programa. Quando um usuário fornece entrada inválida, o sistema de tempo de execução Java lança uma exceção para sinalizar que algo deu errado. O programa pode capturar essas exceções e tratá-las apropriadamente, em vez de travar.

A estrutura básica para o tratamento de exceções em Java é o bloco try-catch:

try {
    // Code that might throw an exception
} catch (ExceptionType e) {
    // Code to handle the exception
}

Modificando Nosso Programa para Lidar com Exceções

Vamos atualizar nosso programa para lidar com a InputMismatchException que ocorre quando o usuário insere uma entrada não numérica:

  1. Abra o arquivo UserInputDemo.java no WebIDE.

  2. Modifique o código para incluir o tratamento de exceções:

import java.util.Scanner;
import java.util.InputMismatchException;

public class UserInputDemo {
    public static void main(String[] args) {
        // Create a Scanner object to read input
        Scanner scanner = new Scanner(System.in);

        try {
            // Prompt the user for their age
            System.out.print("Please enter your age: ");

            // Read the input
            int age = scanner.nextInt();

            // Display the entered age
            System.out.println("You entered: " + age);
        } catch (InputMismatchException e) {
            // Handle the exception if non-numeric input is provided
            System.out.println("Error: Please enter a valid numeric age.");
        } finally {
            // Close the scanner in the finally block to ensure it always gets closed
            scanner.close();
        }
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

  2. Compile o programa atualizado:

javac UserInputDemo.java
  1. Execute o programa:
java UserInputDemo
  1. Tente inserir um valor não numérico, como twenty-five. Em vez de travar, o programa agora exibe:
Please enter your age: twenty-five
Error: Please enter a valid numeric age.

Melhorando Nosso Tratamento de Exceções

Nossa implementação atual lida com a exceção, mas sai imediatamente. Vamos melhorá-la, dando ao usuário várias tentativas para inserir uma idade válida:

  1. Abra o arquivo UserInputDemo.java no WebIDE.

  2. Modifique o código para permitir várias tentativas:

import java.util.Scanner;
import java.util.InputMismatchException;

public class UserInputDemo {
    public static void main(String[] args) {
        // Create a Scanner object to read input
        Scanner scanner = new Scanner(System.in);

        boolean validInput = false;
        int age = 0;

        // Keep trying until valid input is received
        while (!validInput) {
            try {
                // Prompt the user for their age
                System.out.print("Please enter your age: ");

                // Read the input
                age = scanner.nextInt();

                // If we get here, the input was valid
                validInput = true;
            } catch (InputMismatchException e) {
                // Handle the exception if non-numeric input is provided
                System.out.println("Error: Please enter a valid numeric age.");

                // Clear the invalid input from the scanner
                scanner.nextLine();
            }
        }

        // Display the entered age
        System.out.println("You entered: " + age);

        // Close the scanner
        scanner.close();
    }
}
  1. Salve o arquivo.

  2. Compile e execute o programa novamente:

javac UserInputDemo.java
java UserInputDemo
  1. Tente inserir uma entrada inválida primeiro, depois uma válida:
Please enter your age: twenty-five
Error: Please enter a valid numeric age.
Please enter your age: 25
You entered: 25

Agora, nosso programa dá ao usuário várias chances de fornecer entrada válida. Esta é uma melhoria significativa no tratamento de entrada inválida de forma graciosa.

Implementando a Validação de Entrada com Declarações Condicionais

Além do tratamento de exceções, podemos usar declarações condicionais para validar a entrada do usuário. Essa abordagem nos permite implementar regras de validação personalizadas antes de processar a entrada.

Entendendo a Validação de Entrada

A validação de entrada é o processo de verificar a entrada do usuário para garantir que ela atenda a critérios específicos antes de processá-la. Por exemplo, podemos querer garantir que um valor de idade não seja apenas um número, mas também esteja dentro de uma faixa razoável.

Adicionando Validação de Faixa ao Nosso Programa

Vamos aprimorar nosso programa para validar que o usuário insira uma idade entre 0 e 120:

  1. Abra o arquivo UserInputDemo.java no WebIDE.

  2. Modifique o código para incluir a validação de faixa:

import java.util.Scanner;
import java.util.InputMismatchException;

public class UserInputDemo {
    public static void main(String[] args) {
        // Create a Scanner object to read input
        Scanner scanner = new Scanner(System.in);

        boolean validInput = false;
        int age = 0;

        // Keep trying until valid input is received
        while (!validInput) {
            try {
                // Prompt the user for their age
                System.out.print("Please enter your age (0-120): ");

                // Read the input
                age = scanner.nextInt();

                // Check if the age is within a valid range
                if (age < 0 || age > 120) {
                    System.out.println("Error: Age must be between 0 and 120.");
                } else {
                    // If we get here, the input was valid
                    validInput = true;
                }
            } catch (InputMismatchException e) {
                // Handle the exception if non-numeric input is provided
                System.out.println("Error: Please enter a valid numeric age.");

                // Clear the invalid input from the scanner
                scanner.nextLine();
            }
        }

        // Display the entered age
        System.out.println("You entered: " + age);

        // Close the scanner
        scanner.close();
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

  2. Compile o programa:

javac UserInputDemo.java
  1. Execute o programa:
java UserInputDemo
  1. Teste o programa com diferentes entradas:

    • Insira uma idade válida (por exemplo, 25):
    Please enter your age (0-120): 25
    You entered: 25
    • Insira uma idade negativa:
    Please enter your age (0-120): -5
    Error: Age must be between 0 and 120.
    Please enter your age (0-120):
    • Insira uma idade acima de 120:
    Please enter your age (0-120): 150
    Error: Age must be between 0 and 120.
    Please enter your age (0-120):
    • Insira um valor não numérico:
    Please enter your age (0-120): twenty-five
    Error: Please enter a valid numeric age.
    Please enter your age (0-120):

Criando um Exemplo Mais Complexo: Formulário de Registro de Usuário

Vamos criar um exemplo mais abrangente que valida vários campos para um formulário de registro de usuário:

  1. Crie um novo arquivo chamado UserRegistration.java no WebIDE.

  2. Adicione o seguinte código ao arquivo:

import java.util.Scanner;

public class UserRegistration {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);

        // Get and validate username
        String username = getValidUsername(scanner);

        // Get and validate age
        int age = getValidAge(scanner);

        // Get and validate email
        String email = getValidEmail(scanner);

        // Display the registration information
        System.out.println("\nRegistration Successful!");
        System.out.println("Username: " + username);
        System.out.println("Age: " + age);
        System.out.println("Email: " + email);

        scanner.close();
    }

    private static String getValidUsername(Scanner scanner) {
        String username;
        boolean validUsername = false;

        do {
            System.out.print("Enter username (3-15 characters): ");
            username = scanner.nextLine().trim();

            if (username.length() < 3 || username.length() > 15) {
                System.out.println("Error: Username must be between 3 and 15 characters.");
            } else {
                validUsername = true;
            }
        } while (!validUsername);

        return username;
    }

    private static int getValidAge(Scanner scanner) {
        int age = 0;
        boolean validAge = false;

        while (!validAge) {
            try {
                System.out.print("Enter your age (0-120): ");
                age = Integer.parseInt(scanner.nextLine());

                if (age < 0 || age > 120) {
                    System.out.println("Error: Age must be between 0 and 120.");
                } else {
                    validAge = true;
                }
            } catch (NumberFormatException e) {
                System.out.println("Error: Please enter a valid numeric age.");
            }
        }

        return age;
    }

    private static String getValidEmail(Scanner scanner) {
        String email;
        boolean validEmail = false;

        do {
            System.out.print("Enter your email: ");
            email = scanner.nextLine().trim();

            // Simple email validation: must contain @ and a period after @
            if (!email.contains("@") || email.indexOf('.', email.indexOf('@')) == -1) {
                System.out.println("Error: Please enter a valid email address.");
            } else {
                validEmail = true;
            }
        } while (!validEmail);

        return email;
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

  2. Compile o programa:

javac UserRegistration.java
  1. Execute o programa:
java UserRegistration
  1. Siga as instruções para inserir um nome de usuário, idade e e-mail. O programa validará cada entrada e prosseguirá somente quando dados válidos forem inseridos.

Sequência de entrada válida de exemplo:

Enter username (3-15 characters): johnsmith
Enter your age (0-120): 30
Enter your email: john.smith@example.com

Registration Successful!
Username: johnsmith
Age: 30
Email: john.smith@example.com

Este exemplo mais abrangente demonstra como validar diferentes tipos de entrada do usuário usando tratamento de exceções e validação condicional.

Usando Expressões Regulares para Validação de Entrada

Expressões regulares (regex) fornecem uma maneira poderosa de validar padrões de entrada complexos, como endereços de e-mail, números de telefone e senhas. Neste passo, aprenderemos como usar expressões regulares em Java para realizar validação de entrada avançada.

Entendendo as Expressões Regulares

Uma expressão regular é uma sequência de caracteres que define um padrão de pesquisa. Esses padrões podem ser usados para validar se uma string está em conformidade com um formato específico. Java fornece o pacote java.util.regex, que inclui as classes Pattern e Matcher para trabalhar com expressões regulares.

Adicionando Validação Regex ao Nosso Programa UserRegistration

Vamos aprimorar nosso programa UserRegistration para usar expressões regulares para uma validação de entrada mais robusta:

  1. Abra o arquivo UserRegistration.java no WebIDE.

  2. Modifique o arquivo para incluir a validação regex:

import java.util.Scanner;
import java.util.regex.Pattern;
import java.util.regex.Matcher;

public class UserRegistration {
    // Regular expression patterns
    private static final String USERNAME_PATTERN = "^[a-zA-Z0-9_]{3,15}$";
    private static final String EMAIL_PATTERN = "^[a-zA-Z0-9_+&*-]+(?:\\.[a-zA-Z0-9_+&*-]+)*@(?:[a-zA-Z0-9-]+\\.)+[a-zA-Z]{2,7}$";
    private static final String PHONE_PATTERN = "^\\d{3}-\\d{3}-\\d{4}$";

    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);

        // Get and validate username
        String username = getValidUsername(scanner);

        // Get and validate age
        int age = getValidAge(scanner);

        // Get and validate email
        String email = getValidEmail(scanner);

        // Get and validate phone number
        String phone = getValidPhone(scanner);

        // Display the registration information
        System.out.println("\nRegistration Successful!");
        System.out.println("Username: " + username);
        System.out.println("Age: " + age);
        System.out.println("Email: " + email);
        System.out.println("Phone: " + phone);

        scanner.close();
    }

    private static String getValidUsername(Scanner scanner) {
        String username;
        boolean validUsername = false;
        Pattern pattern = Pattern.compile(USERNAME_PATTERN);

        do {
            System.out.print("Enter username (3-15 alphanumeric characters or underscore): ");
            username = scanner.nextLine().trim();

            Matcher matcher = pattern.matcher(username);
            if (!matcher.matches()) {
                System.out.println("Error: Username must be 3-15 characters long and contain only letters, numbers, or underscores.");
            } else {
                validUsername = true;
            }
        } while (!validUsername);

        return username;
    }

    private static int getValidAge(Scanner scanner) {
        int age = 0;
        boolean validAge = false;

        while (!validAge) {
            try {
                System.out.print("Enter your age (0-120): ");
                age = Integer.parseInt(scanner.nextLine());

                if (age < 0 || age > 120) {
                    System.out.println("Error: Age must be between 0 and 120.");
                } else {
                    validAge = true;
                }
            } catch (NumberFormatException e) {
                System.out.println("Error: Please enter a valid numeric age.");
            }
        }

        return age;
    }

    private static String getValidEmail(Scanner scanner) {
        String email;
        boolean validEmail = false;
        Pattern pattern = Pattern.compile(EMAIL_PATTERN);

        do {
            System.out.print("Enter your email: ");
            email = scanner.nextLine().trim();

            Matcher matcher = pattern.matcher(email);
            if (!matcher.matches()) {
                System.out.println("Error: Please enter a valid email address.");
            } else {
                validEmail = true;
            }
        } while (!validEmail);

        return email;
    }

    private static String getValidPhone(Scanner scanner) {
        String phone;
        boolean validPhone = false;
        Pattern pattern = Pattern.compile(PHONE_PATTERN);

        do {
            System.out.print("Enter your phone number (format: 123-456-7890): ");
            phone = scanner.nextLine().trim();

            Matcher matcher = pattern.matcher(phone);
            if (!matcher.matches()) {
                System.out.println("Error: Please enter a valid phone number in the format 123-456-7890.");
            } else {
                validPhone = true;
            }
        } while (!validPhone);

        return phone;
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

  2. Compile o programa:

javac UserRegistration.java
  1. Execute o programa:
java UserRegistration
  1. Teste o programa com diferentes entradas:

    • Tente inserir um nome de usuário inválido (muito curto, contendo caracteres especiais):
    Enter username (3-15 alphanumeric characters or underscore): a$
    Error: Username must be 3-15 characters long and contain only letters, numbers, or underscores.
    Enter username (3-15 alphanumeric characters or underscore):
    • Tente inserir um e-mail inválido (faltando @ ou domínio):
    Enter username (3-15 alphanumeric characters or underscore): johndoe
    Enter your age (0-120): 25
    Enter your email: johndoe.com
    Error: Please enter a valid email address.
    Enter your email:
    • Tente inserir um número de telefone inválido (formato incorreto):
    Enter username (3-15 alphanumeric characters or underscore): johndoe
    Enter your age (0-120): 25
    Enter your email: john.doe@example.com
    Enter your phone number (format: 123-456-7890): 1234567890
    Error: Please enter a valid phone number in the format 123-456-7890.
    Enter your phone number (format: 123-456-7890):
    • Insira todas as entradas válidas:
    Enter username (3-15 alphanumeric characters or underscore): johndoe
    Enter your age (0-120): 25
    Enter your email: john.doe@example.com
    Enter your phone number (format: 123-456-7890): 123-456-7890
    
    Registration Successful!
    Username: johndoe
    Age: 25
    Email: john.doe@example.com
    Phone: 123-456-7890

Entendendo os Padrões de Expressões Regulares

Vamos examinar os padrões de expressões regulares usados em nosso programa:

  1. USERNAME_PATTERN: ^[a-zA-Z0-9_]{3,15}$

    • ^ e $ garantem que o padrão corresponda à string inteira
    • [a-zA-Z0-9_] corresponde a qualquer letra (maiúscula ou minúscula), número ou sublinhado
    • {3,15} especifica que o comprimento deve estar entre 3 e 15 caracteres
  2. EMAIL_PATTERN: ^[a-zA-Z0-9_+&*-]+(?:\\.[a-zA-Z0-9_+&*-]+)*@(?:[a-zA-Z0-9-]+\\.)+[a-zA-Z]{2,7}$

    • Este padrão valida endereços de e-mail de acordo com regras comuns
    • Ele garante que o e-mail tenha uma parte de nome de usuário, um símbolo @ e um domínio
  3. PHONE_PATTERN: ^\\d{3}-\\d{3}-\\d{4}$

    • \\d corresponde a qualquer dígito (0-9)
    • {3} e {4} especificam o número de dígitos
    • - corresponde ao caractere literal hífen

Expressões regulares são uma ferramenta poderosa para validação de entrada, mas podem ser complexas. À medida que você se sentir mais confortável com elas, poderá criar padrões de validação mais sofisticados para seus aplicativos.

Criando um Sistema Completo de Validação de Formulário

Neste passo final, construiremos um sistema completo de validação de formulário que incorpora todas as técnicas que aprendemos. Criaremos um sistema de validação mais modular e reutilizável que pode ser facilmente estendido para diferentes aplicações.

Criando uma Classe Utilitária de Validação

Vamos começar criando uma classe utilitária que encapsula nossos métodos de validação:

  1. Crie um novo arquivo chamado InputValidator.java no WebIDE.

  2. Adicione o seguinte código ao arquivo:

import java.util.regex.Pattern;
import java.util.regex.Matcher;

/**
 * Utility class for validating user input
 */
public class InputValidator {
    // Regular expression patterns
    private static final String USERNAME_PATTERN = "^[a-zA-Z0-9_]{3,15}$";
    private static final String EMAIL_PATTERN = "^[a-zA-Z0-9_+&*-]+(?:\\.[a-zA-Z0-9_+&*-]+)*@(?:[a-zA-Z0-9-]+\\.)+[a-zA-Z]{2,7}$";
    private static final String PHONE_PATTERN = "^\\d{3}-\\d{3}-\\d{4}$";
    private static final String PASSWORD_PATTERN = "^(?=.*[0-9])(?=.*[a-z])(?=.*[A-Z])(?=.*[@#$%^&+=])(?=\\S+$).{8,}$";

    /**
     * Validates a username
     * @param username The username to validate
     * @return true if the username is valid, false otherwise
     */
    public static boolean isValidUsername(String username) {
        if (username == null) {
            return false;
        }
        Pattern pattern = Pattern.compile(USERNAME_PATTERN);
        Matcher matcher = pattern.matcher(username);
        return matcher.matches();
    }

    /**
     * Validates an email address
     * @param email The email to validate
     * @return true if the email is valid, false otherwise
     */
    public static boolean isValidEmail(String email) {
        if (email == null) {
            return false;
        }
        Pattern pattern = Pattern.compile(EMAIL_PATTERN);
        Matcher matcher = pattern.matcher(email);
        return matcher.matches();
    }

    /**
     * Validates a phone number
     * @param phone The phone number to validate
     * @return true if the phone number is valid, false otherwise
     */
    public static boolean isValidPhone(String phone) {
        if (phone == null) {
            return false;
        }
        Pattern pattern = Pattern.compile(PHONE_PATTERN);
        Matcher matcher = pattern.matcher(phone);
        return matcher.matches();
    }

    /**
     * Validates an age
     * @param age The age to validate
     * @return true if the age is valid, false otherwise
     */
    public static boolean isValidAge(int age) {
        return age >= 0 && age <= 120;
    }

    /**
     * Validates a password
     * @param password The password to validate
     * @return true if the password is valid, false otherwise
     */
    public static boolean isValidPassword(String password) {
        if (password == null) {
            return false;
        }
        Pattern pattern = Pattern.compile(PASSWORD_PATTERN);
        Matcher matcher = pattern.matcher(password);
        return matcher.matches();
    }

    /**
     * Gets the error message for an invalid username
     * @return The error message
     */
    public static String getUsernameErrorMessage() {
        return "Username must be 3-15 characters long and contain only letters, numbers, or underscores.";
    }

    /**
     * Gets the error message for an invalid email
     * @return The error message
     */
    public static String getEmailErrorMessage() {
        return "Please enter a valid email address.";
    }

    /**
     * Gets the error message for an invalid phone number
     * @return The error message
     */
    public static String getPhoneErrorMessage() {
        return "Please enter a valid phone number in the format 123-456-7890.";
    }

    /**
     * Gets the error message for an invalid age
     * @return The error message
     */
    public static String getAgeErrorMessage() {
        return "Age must be between 0 and 120.";
    }

    /**
     * Gets the error message for an invalid password
     * @return The error message
     */
    public static String getPasswordErrorMessage() {
        return "Password must be at least 8 characters long and contain at least one digit, one lowercase letter, one uppercase letter, one special character, and no whitespace.";
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

Criando um Formulário de Registro Completo

Agora, vamos criar uma nova versão do nosso formulário de registro que usa a classe InputValidator:

  1. Crie um novo arquivo chamado CompleteRegistrationForm.java no WebIDE.

  2. Adicione o seguinte código ao arquivo:

import java.util.Scanner;

public class CompleteRegistrationForm {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);

        // Collect and validate user information
        String username = getValidInput(scanner, "Username", InputValidator::isValidUsername, InputValidator.getUsernameErrorMessage());
        int age = getValidAge(scanner);
        String email = getValidInput(scanner, "Email", InputValidator::isValidEmail, InputValidator.getEmailErrorMessage());
        String phone = getValidInput(scanner, "Phone number (format: 123-456-7890)", InputValidator::isValidPhone, InputValidator.getPhoneErrorMessage());
        String password = getValidInput(scanner, "Password", InputValidator::isValidPassword, InputValidator.getPasswordErrorMessage());

        // Display the registration information
        System.out.println("\nRegistration Successful!");
        System.out.println("Username: " + username);
        System.out.println("Age: " + age);
        System.out.println("Email: " + email);
        System.out.println("Phone: " + phone);
        System.out.println("Password: " + maskPassword(password));

        scanner.close();
    }

    /**
     * Generic method to get valid input from the user
     * @param scanner The scanner to read input
     * @param fieldName The name of the field being validated
     * @param validator The validation function
     * @param errorMessage The error message to display
     * @return The validated input
     */
    private static String getValidInput(Scanner scanner, String fieldName, java.util.function.Predicate<String> validator, String errorMessage) {
        String input;
        boolean validInput = false;

        do {
            System.out.print("Enter your " + fieldName + ": ");
            input = scanner.nextLine().trim();

            if (!validator.test(input)) {
                System.out.println("Error: " + errorMessage);
            } else {
                validInput = true;
            }
        } while (!validInput);

        return input;
    }

    /**
     * Gets a valid age from the user
     * @param scanner The scanner to read input
     * @return The validated age
     */
    private static int getValidAge(Scanner scanner) {
        int age = 0;
        boolean validAge = false;

        while (!validAge) {
            try {
                System.out.print("Enter your age (0-120): ");
                age = Integer.parseInt(scanner.nextLine());

                if (!InputValidator.isValidAge(age)) {
                    System.out.println("Error: " + InputValidator.getAgeErrorMessage());
                } else {
                    validAge = true;
                }
            } catch (NumberFormatException e) {
                System.out.println("Error: Please enter a valid numeric age.");
            }
        }

        return age;
    }

    /**
     * Masks a password for display
     * @param password The password to mask
     * @return The masked password
     */
    private static String maskPassword(String password) {
        if (password == null || password.isEmpty()) {
            return "";
        }
        return "*".repeat(password.length());
    }
}
  1. Salve o arquivo pressionando Ctrl+S.

  2. Compile ambos os arquivos Java:

javac InputValidator.java
javac CompleteRegistrationForm.java
  1. Execute o programa do formulário de registro:
java CompleteRegistrationForm
  1. Siga as instruções para inserir informações válidas para cada campo. O programa validará cada entrada de acordo com as regras definidas na classe InputValidator.

Interação de exemplo:

Enter your Username: john_doe
Enter your age (0-120): 35
Enter your Email: john.doe@example.com
Enter your Phone number (format: 123-456-7890): 123-456-7890
Enter your Password: weakpw
Error: Password must be at least 8 characters long and contain at least one digit, one lowercase letter, one uppercase letter, one special character, and no whitespace.
Enter your Password: P@ssw0rd123

Registration Successful!
Username: john_doe
Age: 35
Email: john.doe@example.com
Phone: 123-456-7890
Password: ***********

Benefícios Desta Abordagem

A abordagem que adotamos neste exemplo final oferece várias vantagens:

  1. Modularidade: A lógica de validação é separada em uma classe utilitária reutilizável.
  2. Extensibilidade: Novas regras de validação podem ser facilmente adicionadas à classe InputValidator.
  3. Manutenibilidade: As mensagens de erro são centralizadas e podem ser facilmente atualizadas.
  4. Reuso de Código: O método getValidInput é genérico e pode ser usado para diferentes tipos de entrada.
  5. Segurança: A senha é mascarada quando exibida ao usuário.

Este design segue bons princípios de engenharia de software e facilita a adaptação do sistema de validação para diferentes aplicações.

Resumo

Neste laboratório, você aprendeu como lidar efetivamente com entradas de usuário inválidas em programas Java. Você progrediu de uma compreensão básica do tratamento de entrada para a implementação de um sistema de validação abrangente. Aqui está um resumo do que você realizou:

  1. Criou um programa Java básico que coleta a entrada do usuário usando a classe Scanner
  2. Implementou o tratamento de exceções para gerenciar com elegância entradas inválidas
  3. Adicionou validação condicional para garantir que a entrada atenda a critérios específicos
  4. Usou expressões regulares para validação avançada baseada em padrões
  5. Construiu um sistema de validação modular e reutilizável com uma classe utilitária

Essas técnicas são essenciais para o desenvolvimento de aplicações Java robustas que podem lidar com a natureza imprevisível da entrada do usuário. Ao validar e tratar adequadamente a entrada inválida, você pode evitar falhas no programa, manter a integridade dos dados e fornecer uma melhor experiência ao usuário.

Ao continuar sua jornada de programação Java, lembre-se de que a validação de entrada não se trata apenas de evitar erros, mas também de aprimorar a segurança e a usabilidade. Os princípios que você aprendeu neste laboratório podem ser aplicados a vários tipos de aplicações, desde programas simples de console até aplicações web complexas.