Lec.9 Midterm & Files (Chapter 10) Jiang (Jen) ZHENG June 20 th, 2005
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 2 Outline About Midterm Remaining for Chapter 7: wrapper & casting About Assignment 3 Intro. To Java Files Writing Text Files PrintWriter & FileWriter PrintWriter & FileOutputStream Reading Text Files BufferedReader & FileReader Object Stream Writing & Reading Binary Files DataInputStream & DataOutputStream End of the Input Stream
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 3 About Midterm Two Things to Emphasize: statistic variable How to implement interface (the last problem) …
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 4 Wrappers We know each primitive type has a wrapper class: The wrapper classes also provide extra useful functionality for these types Ex: Integer.parseInt() is a static method that enables us to convert from a String into an int Ex: Character.isLetter() is a static method that tests if a letter is a character or not See more in API int Integer double Double
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 5 Wrappers and Casting Ex: Object [] A = new Object[10]; // A[0] = 50; // This is illegal, since 50 is not // an Object A[0] = new Integer(50); // This is fine A[1] = new Integer(30); Note that an array of Object can store any Java class (including any wrapper class) However, because the reference is Object, we are restricted in the methods that we can use Recall from our discussion of polymorphism that the superclass reference cannot “see down” into the subclass details
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 6 Wrappers and Casting Thus, if we want to access anything specific to our wrapper class, we must first cast the reference: Integer i = (Integer) A[0]; Integer j = (Integer) A[1]; if (i.compareTo(j) == 0) System.out.println(i + “ == “ + j); We would get an error if we tried if (A[i].compareTo(A[j])) Also note that if we want to do any “math” with our wrappers, we need to get the underlying primitive values
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 7 “Operations” with Wrappers // Integer k = i + j; // This is illegal The actual computation is actually quite roundabout: Integer k = new Integer(i.intValue() + j.intValue()); In words: Get the primitive value of each Integer object, add them, then create a new Integer object with the result This leads back to the question: Why do we want to bother with this? Aren’t we better off just using int values instead of these wrappers? There are definite benefits to having the data represented in a class Let’s see what they are
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 8 “Generic” Operations Let’s look at a simple example that should already be familiar to you: Sorting Earlier in the term we looked at SelectionSort See Slides The code was written to specifically sort ints: static void sort(int[] data) What if we want to sort floats, or doubles, or Strings, or any other Java type? We need to write a new method for each one!!! The argument array must match the parameter array Or do we?? Can we write a single method that can sort anything? Discuss
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 9 “Generic” Operations Consider the Comparable interface: It contains one method: int compareTo(Object r); Returns a negative number if the current object is less than r, 0 if the current object equals r and a positive number if the current object is greater than r Look at Comparable in the API Consider what we need to know to sort data: is A[i] less than, equal to or greater than A[j] Thus, we can sort Comparable data without knowing anything else about it Awesome! Polymorphism allows this to work
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 10 “Generic” Operations Think of the objects we want to sort as “black boxes” We know we can compare them because they implement Comparable We don’t know (or need to know) anything else about them Show on board Thus, a single sort method will work for an array of any Comparable class Let’s write it now, altering the code we already know from our simple sort method See Sorting.java and ex17.java
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 11 Assignment 3 One Extra Credit Option (proposed by Shaleah): Besides the Batter statistics, you can define the Pitcher statistics as well. Earned Run Average (ERA) (calculated by 9*Earned Runs / Innings Pitched) So for each pitcher, there are two scores Earned Runs and Innings Pitched. You program should be able to sort Pitchers based on the ERA score like what you can do for batters. Think about how to use the inheritance and polymorphisms concepts.
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 12 Intro. to Java Files So far Our programs have read input from the keyboard and written output to the monitor This works fine in some situations, but is not so good in others: What if we have a large amount of output that we need to save? What if we need to initialize a database that is used in our program? What if output from one program must be input to another?
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 13 Intro. to Java Files In these situations we need to use files Most files can be classified into two groups: 1) Text Files Data is a sequence of ASCII characters stored sequentially Any “larger” data types are still stored as characters and must be “built” when they are read in Ex: Strings are sequences of characters Ex: ints are also sequences of characters, but interpreted in a different way To create an actual int we need to convert the characters – this is what the parseInt method in the Integer class does
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 14 Text Files Ex: “12345” in a file is simply 5 ASCII characters: (5 bytes) To convert it into an actual int requires processing the characters: We know ‘0’ is ASCII 48 So our integer is (49-48)x (50-48)x (51-48)x (52-48)x (53-48)x10 0 This can be done in a nice efficient way using a simple loop, and is what the parseInt method does Let’s do it ourselves to see how it can be done Any suggestions on how to start? See MyInteger.java and ex18.java
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 15 Text Files Advantage of text files: Can read them outside of the program by many different editors or programs Easy to create Disadvantage of text files: Must be converted into the desired types as they are read in (as demonstrated with parseInt) This takes time to do and slows I/O Not the most efficient way to store non-String data Ex: int requires 8 bytes in a text file, but only needs 4 bytes in the computer as an int or in a binary file
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 16 Binary Files 2) Binary Files Data in the file is stored in the same way (or in a “serialized” version) that it is stored in the program We can store arbitrary bytes or we can store “whole” data types, including primitive types (int, double, etc.) and objects (String, any other serializable object type) We will discuss serializable more shortly Advantages: Since data is already in its binary form, reading and writing require little if any conversion and is faster than for text files Non-string data can often be stored more efficiently in its binary form than in ASCII form Question: How to store “12345” in a binary file?
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 17 Binary Files Disadvantage: Data in the files is not readable except via a specific computer program Ex: A Java object in a file can only be read in by a Java program There are reasons to use both of these types of files in various applications
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 18 File Streams In Java, file access is provided through a hierarchy of file and stream classes These allow various different access functionalities implemented in a systematic, consistent way Often we “wrap” streams around others to provide more specific access Stream wrappers are a similar notion to our primitive type wrappers – in both cases we are wrapping an object around other data to increase the functionality of the data However, in this case the data being “wrapped” is already an object
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 19 File and Stream classes Hierarchy in Java (For Writing Text Files) java.lang.Object java.io.Writer java.io.PrintWriter PrintWriter(OutputStream out) PrintWriter(Writer out)PrintWriterOutputStream PrintWriterWriter java.lang.Object java.io.Writer java.io.OutputStreamWriter java.io.FileWriter java.lang.Object java.io.OutputStream java.io.FileOutputStream
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 20 File and Stream classes Hierarchy in Java (For Reading Text Files) java.lang.Object java.io.Reader java.io.BufferedReader BufferedReader(Reader in) BufferedReaderReader java.lang.Object java.io.Reader java.io.InputStreamReader java.io.FileReader FileReader(File file)FileReaderFile FileReader(String fileName)FileReader
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 21 File and Stream classes Hierarchy in Java (For Reading/Writing Binary Files) java.lang.Object java.io.OutputStream java.io.FilterOutputStream Java.io.DataOutputStream DataOutputStream(OutputStream out) java.io.FileOutputStream FileOutputStream(File file) FileOutputStream(String name) java.lang.Object java.io.InputStream java.io.FileInputStream java.io.DataInputStream DataInputStream(InputStream in) java.io.FileInputStream FileInputStream(File file) FileInputStream(String name)
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 22 Writing Text Files (I) One example for writing text to an output file: First we create a FileWriter object: FileWriter fileW = new FileWriter(“hello.txt"); Next we wrap a PrintWriter around it PrintWriter pw; pw = new PrintWriter(fileW); Writing to this file pw.println(“Hello World!”); Closing the file when it is done! pw.close();
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 23 Writing Text Files (II) Another simple example for writing text to an output file: First we create a File object: File theFile = new File("ex19out.txt"); This will not necessarily create a file – it simply associates a logical file with the file name provided Next we wrap a FileOutputStream around it FileOutputStream fo; fo = new FileOutputStream(theFile); The above will start writing at the beginning of the file – we could also open it for append fo = new FileOutputStream(theFile, true); At this point we could write to our file However, FileOutputStream only allows a few primitive writing operations (see API)
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 24 Writing Text Files (II) ( Cont. …) To increase the writing functionality we can wrap another stream around it – PrintWriter PrintWriter outFile = new PrintWriter(fo); This allows us to use print and println for our primitive types and object types We don’t actually need all of the intermediate variables in all cases: PrintWriter p = new PrintWriter(new FileOutputStream(new File(“ex19out.txt”))); – Note that we are still creating 3 objects, but we are wrapping the inner two right away, thereby avoiding the extra variables – See ex19.java
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 25 Reading Text Files What about input? The process is very similar However, now we want to use one or more input streams rather than output streams Let’s write a program to read in the file that we just created and show it on the display To show how console I/O is done in the same way as file I/O, we will include this as well
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 26 Reading Text Files This time we will first ask the user for a file name and read it in However to do so we need to create a reader for our “standard input stream” This is a predefined object called System.in (the object is a static object call “in” in the System class – thus the access via System.in) We wrap an InputStreamReader object and then a BufferedReader object around System.in to give us access to the readLine() method Allows us to read one line of String text at a time from the keyboard BufferedReader keyboard = new BufferedReader(new InputStreamReader(System.in)); String fileName = keyboard.readLine();
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 27 Reading Text Files Next we again create a File object, so that we can test for the existence of the file This is important for reading, since it is an error to try to read from a non-existent file theFile = new File(fileName); Now we need a FileReader and then a BuffereReader Use the constructors in the API to help determine how to wrap your objects BufferedReader fReader = new BufferedReader( new FileReader(theFile)); Finally we can start reading using the readLine() method The call returns the next line in the text file, or null if we have reached the end of the file
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 28 Reading Text Files See ex20.java Remember that BufferedReader objects read in String data, and that we must convert it to the type of data we need once it is read in Can use Integer.parseInt(), Double.parseDouble(), etc. for the primitive types Can use appropriate constructors for object types However, we must know exactly how the file is formatted so we can read it and parse it properly
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 29 Object Streams Can we read in complex Java types without having to carefully parse the input? Yes, as long as the types are Serializable Serializable is an interface in Java that requires the readObject() and writeObject() methods to be implemented However, if we are building a new class from other classes that are already Serializable, we do not have to implement the methods within our new class Rather we just have to declare that our new class implements Serializable
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 30 Object Streams If our class is Serializable, we can read and write entire objects with a single readObject or writeObject method call Let’s look at an example: Writing the objects: ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("ex21data.txt")); for (int i = 0; i < myCDs.length; i++) oos.writeObject(myCDs[i]); Note that the file generated here is NOT text and will not be readable in normal text editors However, restoring the data back to a Java program is now very easy
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 31 Object Streams Reading the objects: ObjectInputStream ois = new ObjectInputStream(new FileInputStream("ex21data.txt")); for (int i = 0; i < myData.length; i++) myData[i] = ois.readObject(); There are some important issues here that are somewhat “hidden” in this example They deal with the possibility of exceptions IO in Java can typically generate various different exceptions, and some of them must be explicitly dealt with Thus the header says “throws exception” We are probably better off handling these, but since we haven’t covered exceptions yet, we’ll defer for now. Exceptions will be covered in Chapter 11. See ex21a.java and ex21b.java
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 32 Reading/Writing Binary Files We discussed previously that numeric data can often be stored more efficiently in binary form than in text form In this case we may want to use a binary file to store it Not an object file, since the data is a primitive type For this we can use a DataOutputStream for output and a DataInputStream for input See API for methods Ex: writeInt(), writeDouble() – DataOutputStream Ex: readInt(), readDouble() – DataInputStream See BinIOTest.java
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 33 Reading/Writing Binary Files Let’s try this and then compare the sizes of the binary and text files During the Lab hours We will generate a number of random ints and random doubles Store each in a text file and in a binary file and compare sizes at the end Note that the size of the integer text file depends greatly on the values of the integers, while the size of the integer binary file is independent of the values If we are storing very small integers, using a text file will actually save us space, but for large integers it will cost us space
CS401/COE401 Summer 2005.Department of Computer Science.University of Pittsburgh.Lecture 9 34 EOF (end-of-file) detection ClassMethod EOF Detected by java.io.DataInputStream readPrimitive() readLine() read() java.io.BufferedReader readLine() read() returns null returns -1 EOFException returns null returns -1