CS 136 - Lecture 32

  1. Reading text files
    1. ReadStream class
    2. Examples
  2. Graph applications
    1. Traversal problems

Reading text files

We previously saw that the DataInputStream class was helpful in allowing us to read a file of data.

Now we'll look at another way of reading files -- in particular, text files. (For example, a Microsoft Word file that had been saved as Text.)

ReadStream class

As before, file operations are pretty straightforward:
// create a new input file with name fileName.
  ReadStream inFile = new ReadStream(new FileInputStream(fileName));
// read string from inFile and store in word
  String word = inFile.readString();
    
// read integer from inFile and store in num
  int num = inFile.readInt();
// close file
  inFile.close();                     

ReadStream found in Bailey's structures package. Don't forget to import java.io.*; for the other io classes used.

Examples


import structure.*;
import java.io.*;

public class ReadStreamDemo
{
   public static void readAndPrint(String fileName)
   // pre: fileName is non-null file name.
   // post: prints the text in the file, 1 word per line.
   {
      try
      {
         ReadStream d = new ReadStream(new FileInputStream(fileName));
         for (String aWord = d.readString(); !aWord.equals(""); aWord = d.readString())
         {
            System.out.println(aWord);
         }
         d.close();
      }
      catch (IOException e) {System.out.println(e.toString());}
   }

   public static int readANumberFile(String fileName)
   // pre: fileName is file containing integers.
   // post: returns sum of integers in the file.
   {
      int theSum = 0;
      try
      {
         ReadStream d = new ReadStream(new FileInputStream(fileName));
         while (!d.eof())
         {
            int aNumber = d.readInt();
            theSum = theSum + aNumber;
         }
         d.close();
      }
      catch (IOException e) {System.out.println(e.toString());}
      return theSum;
   }

   public static void main(String args[])
   {
      readAndPrint("TextDemoFile");
      System.out.println(readANumberFile("NumberFile"));
   }
}

Graph Applications

Traversal problems

Say we wish to serve as travel agent for Berkshire Airlines. We will need to process customer requests to fly from origin city to destination city. We'll start by only checking whether it's possible to fly from origin to destination.

Input files:

FlightFile: Each line is pair of city names representing origin and destination of one (leg of one) flight.
User types in names of pairs of cities. Program responds with message as to whether an itinerary is possible.

  1. Begin by creating graph from the file.
  2. When get request, begin exhaustive search of all cities accessible from origin city until either find destination or no more cities accessible.
How can we do search?
  1. Start at origin, visit it to see if what looking for
  2. If not found go to city, C1, connected to it
  3. Search C1 and all connected to it
  4. If not found check other neighbors and cities connected to them until find it or no more neighbors:
static boolean isPath(Graph g, Object startLabel, Object finishLabel)
{
    g.visit(startLabel);
    if (startLabel.equals(finishLabel))
        return true;
    else
    {
        Iterator nbrIterator;
        boolean found = false;
        for (nbrIterator  = g.neighbors(vertexLabel); 
                nbrIterator.hasMoreElements() && !found;
                nbrIterator.nextElement())
        {
            Object neighbor = nbrIterator.value();
            if (!g.isVisited(neighbor))
                found = isPath(g,neighbor,finishLabel);
        }
        return found;
    }
}
Can call as follows:
    g.reset();
    if (isPath(g,sourceLabel,destinationLabel))
    {...};
Can find all nodes connected to another by a similar program.

Can also do these iteratively:

static boolean isPath(Graph g, Object startLabel, Object finishLabel)
{
    Stack s = new StackList();
    s.push(startLabel);
    g.reset();
    while (!s.isEmpty())
    {
        Object current = s.pop();
        if (!g.isVisited(current))
        {
            g.visit(current);
            if (current.equals(finishLabel))
                return true;
            for (Iterator nbrIterator  = g.neighbors(vertexLabel); 
                                    nbrIterator.hasMoreElements();
                                    nbrIterator.nextElement())
                s.push(nbrIterator.value());
        }
    }
    return false;
}
Complexity: Start by pushing and popping original vertex. Then for each unvisited node, push all neighbors on stack. Sum of degrees of all vertices = 2 * (# edges).
Thus complexity = O(e), if e is number of edges. (Note some vertices may never get reached, so don't have to add O(v).

What order does this do search in?

What would happen if we used a queue instead of a stack?

Breadth-First visits as few vertices as possible before 'backtracking' (removing a vertex from the queue). Thus neighbors of V are visited first, then neighbors of neighbors, etc.

Priority-First Traversal (Priority Queue Based) Vertices to be visited next are put on a priority queue.

What if we wanted to classify all vertices in terms of which component they are in?