3

I need to retrieve and delete a random line from a txt file (the same line). Thus far I've come up with the following code:

 public String returnAndDeleteRandomLine(String dir) throws FileNotFoundException, IOException {
    try (BufferedReader br = new BufferedReader(new FileReader(dir))) {
        //StringBuilder sb = new StringBuilder();
        //System.out.println("Value of line before while() " + line);

        ArrayList fileContents = new ArrayList();
        int maxLines = 0;


        String line = br.readLine();
        //System.out.println("Value of line before while() " + line);

        while (line != null) {
            fileContents.add(line.toString());
            line = br.readLine();
            //System.out.println("Value of line is: " + line);
        }

        System.out.println("Value of maxLines() " + maxLines);

        Random rand = new Random();
        int randomNumber = rand.nextInt(maxLines - 1) + 1;
        System.out.println("Value of randomNumber: " + randomNumber);
        int lineNumber = randomNumber;

        if (fileContents.isEmpty()) {
            return null;
        } else System.out.println("Value of random line: " + fileContents.get(randomNumber).toString());
        return fileContents.get(randomNumber).toString();
    }


 }

But I keep getting different errors. The most recent error was:

Value of maxLines() 0 Exception in thread "main" java.lang.IllegalArgumentException: bound must be positive at java.util.Random.nextInt(Unknown Source) at TransmitToFile.returnAndDeleteRandomLine(TransmitToFile.java:247) at Main.main(Main.java:98)

I could not even work on deleting the line because I'm still unable to retrieve the line.

Subodh Joshi
  • 12,717
  • 29
  • 108
  • 202
Kay Mart
  • 65
  • 3

4 Answers4

1

You forgot so set the value of variable maxLines to nuber of lines in file and since its 0 you get an exception.

You can add new method to get line numbers like this (as shown in this answer: number-of-lines-in-a-file-in-java):

public int countLines(String filename) throws IOException {
        LineNumberReader reader = new LineNumberReader(new FileReader(filename));
        int cnt = 0;
        String lineRead = "";
        while ((lineRead = reader.readLine()) != null) {
        }

        cnt = reader.getLineNumber();
        reader.close();
        return cnt;
    }

And change your code from:

int maxLines = 0;

to:

int maxLines = countLines(dir);

So that the maxLines variable will be the equal to the number of lines in your file.

Community
  • 1
  • 1
Kiki
  • 2,243
  • 5
  • 30
  • 43
  • If the file is empty (maxlines = 0) this solution will still fail, so you should also do a check if(maxLines = 0) return; or something. Probably not a big issue in real life, but worth noteing. – Astrogat Aug 06 '15 at 09:41
1

Random.nextInt(N) delivers 0 .. N-1. As all indices are counting from 0, but humans count from 1, there was a mix-up.

The general code can be done simpler:

public static String returnAndDeleteRandomLine(String dir) throws IOException {
    Path path = Paths.get(dir);
    List<String> lines = Files.readAllLines(path, StandardCharsets.UTF_8);
    if (lines.isEmpty()) {
        throw new IOException("Empty file: " + dir);
    }
    Random rand = new Random();
    int lineIndex = rand.nextInt(lines.size()); // 0 .. lines.size() - 1
    String line = lines.get(lineIndex);

    System.out.printf("Line %d: %s%n", (lineIndex + 1), line);

    lines.remove(lineIndex);
    Files.write(path, lines, StandardCharsets.UTF_8,
            StandardOpenOption.WRITE, StandardOpenOption.TRUNCATE_EXISTING);
    return line;
}
Joop Eggen
  • 107,315
  • 7
  • 83
  • 138
0

The problem is the line

int randomNumber = rand.nextInt(maxLines - 1) + 1;

In the case where maxLines is 0, then you're calling rand.nextInt(-1). Hence the error that this parameter must be positive.

mattinbits
  • 10,370
  • 1
  • 26
  • 35
0

The error is in this line:

int randomNumber = rand.nextInt(maxLines - 1) + 1;

You should add a check to check the size first:

int totalLines = maxLines - 1;
if(totalLines > 0) {
    Random rand = new Random ();
    int randomNumber = rand.nextInt (totalLines) + 1;
    System.out.println("Value of randomNumber: " + randomNumber);
    } else {
        return null;
    }
sjain
  • 23,126
  • 28
  • 107
  • 185