/* --- CSU213 Spring 2006 Lecture Notes --------- Copyright 2006 Viera K. Proulx Lecture 4: Janus */ /* Goals: - practice the design of complex class hierarchies - learn to represent Java program as data - program is data - data drives programs Cosnsider the following data definition. +------+ | IJob |<------------------------+ +------+ | / \ | | | - - - - - - - - - - - - - - - - - - - | | | | | +-----------+ +-----------+ +------------+ | | Sleep | | Read | | BigJob | | +-----------+ +-----------+ +------------+ | | int hours | | Book book |-+ | IJob task1 |----+ +-----------+ +-----------+ | | IJob task2 |----+ | +------------+ v +---------------+ | Book | +---------------+ | String title | | String author | +---------------+ */ // to represent a job interface IJob { } // to represent a sleeping job class Sleep implements IJob { int hours; Sleep(int hours) { this.hours = hours; } } // to represent a reading job class Read implements IJob { Book book; Read(Book book) { this.book = book; } } // to represent a book class Book { String title; String author; Book(String title, String author) { this.title = title; this.author = author; } } // to represent a big job class BigJob implements IJob { IJob task1; IJob task2; BigJob(IJob task1, IJob task2) { this.task1 = task1; this.task2 = task2; } } class Examples { Examples() {} IJob sleep5 = new Sleep(5); IJob sleep3 = new Sleep(3); Book htdp = new Book("HtDP", "FFFK"); Book beach = new Book("Beach Music", "Pat Conroy"); IJob readHtDP = new Read(this.htdp); IJob readBeachMusic = new Read(this.beach); IJob work = new BigJob(this.sleep5, this.readHtDP); IJob play = new BigJob(this.sleep3, this.readBeachMusic); IJob workPlay = new BigJob(this.work, this.play); } /* When we use make a mistake in the definition of the class hierarchies, ProfessorJ finds the error and tells us what is the problem. In order to be able to do so, it must check all the definitions and analyze the information they represent. But to analyze information within a program, we need to represent the information as data. Our goal for today is to represent the Java program shown above as data --- i.e. design the class hiearachy that can represent a Java program (Begginer Professorj program with only class definitions and interface definitions), and make examples of data that represent the information above - the Java program itself. We start by looking at the program and identifying the different kinds of information it contains. We see that the main two parts are interface definitions (we only have one of these - the interface IJob) and class definitions (we have five of them: Sleep, Read, BigJob, Book, and Examples). We will ignore the Examples class for now. Next we look at the interface definition. The only important piece of informatiuon it contains is the name of the interface (IJob). The class definitions are more complicated. Again, each has a name. Some of them implement an interface. It is possible for a class to implement several interfaces --- we will see this later. The third kind of infomation that completes the class definition is a list of field definitions. Each field definition consists of a type of the field and its name. This leads to the following data defintions: A Java program consists of -- list of Interface definitions -- list of Class definitions An Interface definition consists of -- name (a String) (and for now nothing else, though this will change) A Class definition consists of -- name (a String) -- list of field declarations A Field declaration consists of -- field type (a String: IntfDef name or ClassDef name or PrimitiveType) -- field name (a String) A PrimitiveType is one of "int" "boolean" "String" Note: We could define the Type as a class by itself, but for now we just make it a String that has to have a correct value. In one of the assignments your job will be to verify that a program definition is correct --- the fields types are valid, the field names are not repeated, the names of interfaces a class implements are known, etc. Note: There are restrictions on what kind of String-s can be valid Java names - it would be a task of a separate program to make sure that a new name we wish to use does indeed satisfy the rules for a Java identifier. We assume here that the names have been chosen correctly. The above semi-formal data definitions can be translated into the following class diagram: +-----------------------+ | Program | +-----------------------+ +-| ILoIntfDef interfaces | | | ILoClassDef classes |--+ | +-----------------------+ | | | v | +------------+ | +------------>| ILoIntfDef |<---------------+ | | +------------+ | | | +------------+ | | | / \ | | | --- | | | | | | | ---------------------- | | | | | | | | +-------------+ +-----------------+ | | | | MTLoIntfDef | | ConsLoIntfDef | | | | +-------------+ +-----------------+ | | | +-------------+ +-| IntfDef first | | | | | | ILoIntfDef rest |----+ | | | +-----------------+ | | | | | v | | +-------------+ | | | IntfDef | | | +-------------+ | | | String name | | | +-------------+ | | | | +---------------------------+ | | | v | +-------------+ | | ILoClassDef |<----------------+ | +-------------+ | | +-------------+ | | / \ | | --- | | | | | ----------------------- | | | | | | +--------------+ +------------------+ | | | MTLoClassDef | | ConsLoClassDef | | | +--------------+ +------------------+ | | +--------------+ +-| ClassDef first | | | | | ILoClassDef rest |----+ | | +------------------+ | | | v | +-----------------------+ | | ClassDef | | +-----------------------+ | | String name | +----| ILoIntfDef interfaces | | ILoField fields |--+ +-----------------------+ | | +------------+ | v +----------+ | ILoField |<--------------+ +----------+ | +----------+ | / \ | --- | | | -------------------- | | | | +-----------+ +---------------+ | | MTLoField | | ConsLoField | | +-----------+ +---------------+ | +-----------+ +-| Field first | | | | ILoField rest |----+ | +---------------+ | v +-------------+ | Field | +-------------+ | String type | | String name | +-------------+ We will now show how someparts of our program can be represented as data within this class hierarchy: // interface definition for IJob IntfDef ijobDef = new IntfDef("IJob"); // an empty list of interfaces ILoIntfDef mtinfdefs = new MTLoIntfDef(); // list of interfaces - with only IJob in it ILoIntfDef intfList = new ConsLoIntfDef(this.ijobDef, this.mtinfdefs); // field definitions Field intHours = new Field("int", "hours"); Field stringTitle = new Field("String", "title"); Field stringAuthor = new Field("String", 'author"); // empty list of fields ILoField mtfields = new MTLoField(); // fields for the class Sleep ILoField sleepFields = new ConsLoField(this.intHours, this.mtfields); // class definition for the class Sleep ClassDef sleepClass = new ClassDef("Sleep", this.intfList, this.sleepFields); // fields for the class Book ILoField bookFields = new ConsLoField(this.stringTitle, new ConsLoField(this.stringAuthor, this.mtfields)); // class definition for the class Book Classdef bookClass = new ClassDef("Book", this.mtinfdefs, this.bookFields); The rest is left to the reader ... */