Files

So far the data in our programme has only existed while the programme runs, and data has either been hard coded into our programme or input by the user. It would be useful if we could make use of data that is stored more permanently on disk.

Typically we might read the data into an array, so the example that follows would require us to use (and import) the File, Scanner and ArrayList packages as follows:

import java.io.File;
import java.util.Scanner;
import java.util.ArrayList;

The listing below shows a method which will read a text file located in the src folder of the Java project

static ArrayList<String> arrayListFromDataFile(){
    ArrayList<String> nameList = new ArrayList<String>();
    File dataFile = new File("src/data.txt");
    try
    {
        Scanner fileScanner = new Scanner(dataFile);
        while (fileScanner.hasNext()){
            nameList.add(fileScanner.nextLine());
        }
        fileScanner.close();
    }
    catch (FileNotFoundException e) {
        System.out.println("Cannot read from file");
    }
    return nameList;
}

Anticipating errors

One of the issues with reading files, is that the file may not exist, or may not have the data in the format we expect - this could potentially be outside our control as the user could modify the file. If that happens the programme would generate an error (formally known as an exception).

The solution to dealing with errors (rather than allowing the programme to crash, is to use something called a try catch block). Essentially we attempt to execute some code, and if it fails we do something else instead. try catch blocks should be used sparingly and only when code might fail due to circumstances beyond our control (not to get around bad programming!).

In the above example, the code which might fail is when we try and create a scanner using a file (Java does not care if the dataFile object doesn't refer to a real file, but the scanner cares if it can't access the file). In the example below, if we cannot read from file then the execution of code will jump to inside the catch block, so the Array will remain empty, and, aside from a message, the method will fail silently (i.e. the programme will not crash).

Reading data from file

In the above code, we use a while loop to ascertain if there is more data to be read (using an Iterator), and while there is, read it in as a String and add it to the Array. As you will be aware, the scanner can read different data types (e.g. by using nextInt() for example). If data other than an entire line String is not read, it will by default look for spaces to seperate values, you can change what it expects to seperate values using the useDelimiter() method, and for example pass in a comma.

Once we are finished with the Scanner we close it, to ensure the programme does not continue to consume resources it does not need.

Task

  1. Create a plain text file (with the .txt extension) containing a list of names (each name on a new line).
  2. Save the file in the src folder of your project
  3. Use the above code (or an adaptation of it) within a new commandline project to read the items into an ArrayList and then output each one to the console

Task - numbers

  1. Create another plain text file, this time save it with the extension .dat (you may need to rename it after creation)
  2. Fill the file with a series of integer values, each on a new line
  3. Place the file in the Java Project, e.g. in the src folder
  4. Write a programme which will read the values from the file and provide the total, and average of the values
  5. Test your programme
  6. Modify the file so that the numbers are on the same line, separated by commas
  7. Modify the programme so that it works again

Advanced Task

  1. Create a file which includes a mix of words and Integers (seperated by either commas or new lines), in no particular order
  2. Write a programme which will load the words into a ArrayList of strings and the numbers into a corresponding list of Integers. The programme should be written such that it will function regardless of the order of the words and numbers. Once the file is loaded it should output the values of each array, strings first followed by integers.
  3. Test the programme
  4. Modify the file's data and test again

See a model solution if you have difficulty with this (be aware that as with most programming problems there are multiple ways to solve them, so don't worry if your solution works, but looks different).