/* * Lab 3 * * The purpose of today's lab is to make methods for simple classes * and classes with containment; testing. * * Before continuing, please make sure that the language level is set to * "ProfessorJ - Beginner" */ /**********************************************************************/ /* * As a review of the material we learned last week, implement the * Car and Owner classes. The Car class should have a make, * year(an 'int'), price, and Owner. The Owner class should have a * name and age. Remember to follow design recipe and write down your * purpose statements. * * TASK: write these two classes directly following this comment: */ /**********************************************************************/ /**********************************************************************/ /* That was quick, right? Now create a couple of examples of your * Owners - for instance, * - "Dr. Seuss", 101 // we'll call this one drSeuss * - "Matthias Felleisen", 50 // we'll call this one matthias * Now make some examples of Cars - for instance, * - "Porsche 911", 2006, 70000, this.drSeuss // we'll call this one porsche911 * - "Ford Pinto", 1977, 2000, this.matthias // we'll call this one pinto * * TASK: Now add these to the Examples class at the bottom of this * file. */ /**********************************************************************/ /**********************************************************************/ /* * Now, we want to be able to ask questions about these Cars. For * instance, consider the problem of determining whether a car is old * - it's always nice to know whether you're reading an old car. For * this example, we'll consider a car 'old' if it was made before the * year 2000. * * How would we calculate this value? Simply enough, we would retrieve * the year of the car, and then check whether is is less than 2000. * However, repeating that calculation every time we wanted to check * whether a car wa old would be tedious and error-prone. We want to * tie this behavior up in one place so that we don't need to code it * again. Thus, methods. Methods are essentially Scheme functions in * a different wrapper, and we can use them in the same fashion. * * (1) For our oldCar method, we first write a purpose statement and * method header: * * // oldCar: return true if this's year comes before 2000 * boolean oldCar() {...} * * (2) Now add some examples: * pinto.oldCar() // should be true * porsche911.oldCar() // should be false * * (3) Now, the template. We sketch out the pieces of data available * in this method -- i.e. this and the fields. * * ... this.make ... * ... this.owner ... * ... this.year ... * ... this.price ... * * (4) Now, the body and make sure you run the tests. * * boolean oldCar() { * return this.year < 2000; * } * * (5) Finally, in the Examples class: * * boolean oldCarTest1 = this.pinto.oldCar() == true; * boolean oldCarTest2 = this.porsche911.oldCar() == false; * * Some things to notice about this method - we have to specify what * the type of the return value is, which we defined in our purpose * statement. When we call the method on an object, it provides the * object that the method was called on as an implicit argument named * 'this', which we use to access our year information. * * TASK: Using the design recipe, add the method above to your Car * class and try it out on your examples. To do so, run the * program, in the Interactions type * * > Examples e = new Examples(); * > e.testOldCar1 * ... should get true * * > e.testOldCar2 * ... should get true * * or type * > e * and see the values of all fields * */ /* * Functions without arguments are good, but functions with arguments * are even better, as they allow us to compare two things. Say that * I'm into old cars , and want to compare two Cars and ask which is * older. To do that, I'll need to get my hands on another Car object * to compare - an argument. * * Now, it's time to write some methods on your own. * * TASK: Design the method madeBefore(int year) that determines * whether a car was made before some given year */ /* * Now, we'll write a function that takes another Car -- called * 'that'. Since we are passed another Car as an argument named * 'that', we can access the values it contains. So make sure that * your template contains the fields of 'this' and the fields of * 'that'. * * TASK: Using the design recipe, add olderThan(Car that) to your Car * class that determines whether a Car is older than the given * Car. */ /* * Now, we'll write a function that takes an Owner and returns true if * this's owner is the same as the passed in one; we'll call this * method sameOwner(Owner). However in order to find this out we'll * delegate to this's owner and ask it if it is the same as the passed * in Owner. Hence we need to add a method sameOwner(Owner) to the * Owner class first. But before doing that we'll talk a little about * testing values for equality. * * We need to determine whether two instances of the Owner class * represent the same two owners. The method 'sameOwner' can be * defined within the Owner class. We know, that it will * automatically get one argument of the type Owner - the instance * that invoked the method. We will need another argument - the other * instance we want to compare with. * * So the purpose statement and the header become: * * // is this owner the same as the given other owner? * boolean sameOwner(Owner that){...} * * To test ints and booleans for equality we can use the '==' * operatior, e.g. * * 3 == 4 --> false * 3 == 3 --> true * true == true --> true * true == false --> false * * However to test Strings for equality we use the equals method, e.g. * * "one".equals("one") --> true * "one".equals("two") --> false * * HINT: Also the logical AND of to values b1 and b2 is made in * scheme as * * (and b1 b2) * * In Java we write * * b1 && b2 * * TASK: Using the design recipe add the method sameOwner(Owner * that) to the Owner class that returns true if this.name is * the same as that.name and this.age is the same as that.age. * (Remember how to test Strings for equality!) * * TASK: Once you've tested sameOwner(Owner) in the Owner class and * you're satisfied, using the design recipe, write the method * sameOwner(Owner that) in the Car class that delegates to * this.sameOwner(Owner). */ /* * Now, we wish change the price of a car. So we will create a new * car with all the same fields as this car, except for the new * price which is 20% less than the old price. Since, we're showing * an example we'll complete the first part of the design recipe for * you. * * // changePrice: produce a new car whose price is 20% less that the original one * Car changePrice() { * ... * } * * so, for example: * * porsche911.changePrice(); // should produce: * // new Car("Porsche 911", 2006, 56000, this.drSeuss); * pinto.changePrice(); // should produce: * // new Car("pinto", 1977, 1600, this.matthias); * */ // Class for containing examples: class Examples { Examples() {} // Don't mess with this line! // Examples from above: // Owner drSeuss = new Owner("Dr. Seuss", 101); // Owner matthias = new Owner("Matthias Felleisen", 50); // Car porsche911 = new Car("Porsche 911", 2006, 70000, this.drSeuss); // Car pinto = new Car("Ford Pinto", 1977, 2000, this.matthias); /* * Run the following code in your interactions window: * * Examples e = new Examples(); * * and then test out your examples like so: * * e * */ }