Create a Java program that analyzes log files generated by a web server. The program should parse the log files, extract information about HTTP requests (e.g., IP address, request method, URL, response code), and generate a summary report with statistics such as the number of requests per IP address, most frequent URLs, and distribution of response codes.
Here's a Java program that analyzes log files generated by a web server. This program assumes the log file follows the Common Log Format (CLF).

```java
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

public class LogAnalyzer {
    public static void main(String[] args) {
        if (args.length != 1) {
            System.err.println("Usage: java LogAnalyzer <log_file_path>");
            System.exit(1);
        }

        String logFilePath = args[0];
        analyzeLogFile(logFilePath);
    }

    private static void analyzeLogFile(String logFilePath) {
        Map<String, Integer> ipCountMap = new HashMap<>();
        Map<String, Integer> urlCountMap = new HashMap<>();
        Map<Integer, Integer> responseCodeCountMap = new HashMap<>();

        try (BufferedReader br = new BufferedReader(new FileReader(logFilePath))) {
            String line;
            while ((line = br.readLine()) != null) {
                String[] tokens = line.split(" ");
                if (tokens.length >= 9) {
                    String ipAddress = tokens[0];
                    String requestMethodAndUrl = tokens[5] + " " + tokens[6];
                    int responseCode = Integer.parseInt(tokens[8]);

                    ipCountMap.put(ipAddress, ipCountMap.getOrDefault(ipAddress, 0) + 1);
                    urlCountMap.put(requestMethodAndUrl, urlCountMap.getOrDefault(requestMethodAndUrl, 0) + 1);
                    responseCodeCountMap.put(responseCode, responseCodeCountMap.getOrDefault(responseCode, 0) + 1);
                }
            }
        } catch (IOException e) {
            System.err.println("Error reading log file: " + e.getMessage());
            System.exit(1);
        }

        generateSummaryReport(ipCountMap, urlCountMap, responseCodeCountMap);
    }

    private static void generateSummaryReport(Map<String, Integer> ipCountMap,
                                              Map<String, Integer> urlCountMap,
                                              Map<Integer, Integer> responseCodeCountMap) {
        System.out.println("=== Summary Report ===");

        System.out.println("\nNumber of requests per IP address:");
        ipCountMap.entrySet().stream()
                .sorted(Map.Entry.<String, Integer>comparingByValue().reversed())
                .forEach(entry -> System.out.println(entry.getKey() + ": " + entry.getValue()));

        System.out.println("\nMost frequent URLs:");
        urlCountMap.entrySet().stream()
                .sorted(Map.Entry.<String, Integer>comparingByValue().reversed())
                .limit(10)
                .forEach(entry -> System.out.println(entry.getKey() + ": " + entry.getValue()));

        System.out.println("\nDistribution of response codes:");
        responseCodeCountMap.entrySet().stream()
                .sorted(Map.Entry.comparingByKey())
                .forEach(entry -> System.out.println(entry.getKey() + ": " + entry.getValue()));
    }
}
```

To run the program, compile it using `javac LogAnalyzer.java` and then execute it with `java LogAnalyzer <log_file_path>` where `<log_file_path>` is the path to your log file.

The program reads the log file line by line, extracts information about HTTP requests (IP address, request method, URL, response code), and stores them in HashMaps. Finally, it generates a summary report with statistics such as the number of requests per IP address, most frequent URLs, and distribution of response codes.