Space

- Handout -



SILLY PREMISE:

On October 14, 1947 General "Chuck" Yeager flew the ultra-high powered X-1 to a speed of Mach 1.06 which made him the first human being to effectively break the sound barrier. Chuck Yeager was a pioneer. He did something no other human being had ever done. Chuck Yeager was a hero. What he did for the aerospace program was phenomenal. What he did four our society was even more important -- he provided a role model for young kids across America.

But today we are without such heroic role-models who have new territories to conquer. Our society grows continually pallid from day to day. The only people our children have to look up to are such fading "heroes" as the New Kids on the Block, the Teenage Mutant Ninja Turtles, and more recently, the Spice Girls and Hanson. It is time for a resurgence. It is time for a new hero to emerge. That hero is you.

With the advent of the Object-Oriented Programming Paradigm (OOPP) a new territory has been defined. A new manifest destiny declared. One of the early sponsors of the early adventures such as D. B. (Daniel Boone) Connor and R. C. (Robinson Crusoe) Duvall has declared that there is a barrier, much like the vaunted sound barrier Chuck Yeager so daringly destroyed, that cannot be broken in the world of OOPP. This "extensibility barrier" has never been broken before. Right now the agreed upon limit of this barrier is approximately 73%. That is, the design for any Object-Oriented program may only approach but never exceed being 73% extensible. The social ramifications of this are obvious, but for the unindoctrinated I will spell them out: no one has ever written a fully extensible program before!

With this assignment, Space, you will be given an attempt to metaphorically fly Chuck Yeager's X-1, you will be given an opportunity to break his sound barrier. You will be given an attempt to break the extensibility barrier. You will be given a chance to tread in an environment that no one has even dreamed of before. You must succeed, the fate of our children is lying upon your shoulders.

SPECIFICATION:

Your job, as our fateful hero, is to create a program which models a Space simulation (hence the name of the program). In this simulation the user should be able to move a space ship around the screen. Movement, in Space, consists of being able to move forward (Thrust), move backward (Dethrust), turn left and turn right. Since we are in space the ship cannot stop as Newtonian physics apply.

In your simulation there should be at least two types of ships that the user can move around at any given time. One type, called an Attacker, should move very quickly, and fire a weapon when it is Activated. The second type, called an Explorer, should move very slowly, and shine a light in front of it when Activated. Each ship should have its own unique shape as well. Any extra types of ships that you construct will be counted as extra credit.

All ships, as mentioned, should be able to be Activated. What this means is that the ship should do something unique to its type (such as firing a weapon or shining a light) when the user specifies. How does a user specify that a ship should be Activated or even move about? Through the use of input devices. Utilizing GP we have two such methods of doing so. We can either press buttons which effect the ship or we can press keys which will do the same. Your program must support both types of user input but must not allow both to manipulate the ship at the same time.

Finally, the user must be able to change the color of the ship at any given point.

MOTIVATION:

The two main motivating factors in giving this assignment are to teach polymorphism and extensibility. By now these are two words you should be very familiar with. But by familiar I mean that you have heard them over and over again but probably do not know what they really mean. This assignment has been engineered to give you a first hand view of what these actual two ideas mean in practice.

The central idea of this assignment is that everything can be switched in and out at runtime. What the space-ship looks like, what it does when it is "activated", how it is controlled, and how it acts. Many times when we think about the situations like the one we are given in Space, we think "I will have a ship that looks like a line, fires bullets when it is activated, and is controlled with the keys." From that point on we will go design and implement our program in this fashion.

But what happens when the person we are creating this program for decides that they do not like a particular aspect of the program? What happens if the user of our program, in this example, has Carpal Tunnel Syndrome? Obviously we would want to find an alternate way for them to control the ship. How easily can we do this with our current design? What if we want to give the user an option between the two? What happens if in a year a new form of input comes along, how easy will it be for us to add functionality for this device?

All these questions are questions regarding what we call extensibility. The definition of an extensible design for a program is one that can be updated or augmented with a maximization of ease and a minimization of restructuring. If when adding support for a mouse or a new input device we have to redesign our entire program and recode half of it we see that our original design was not very extensible. On the flipside, if adding support is very simple and we do not have to change much or any of our original design and code we say that we have an extensible design and implementation.

So what allows us to be this extensible in our design? The answer, if you have not guessed it already, is polymorphism. Polymorphism is a tool that allows us to construct object relations in such a manner that will allow for our design to become extensible. So what is a good example of polymorphism? Good question. Keeping with the same example, we note that we should be able to change the input device at runtime. But should this affect the ship we are controlling? Should it even matter what type of ship we are controlling? The answer, as it turns out, is no.

Think about the assignment specification for a minute. If the input device cared about what type of ship it was controlling what would happen when we switched the type of the ship? In a less extensible design our program might cease to function: the new ship might not be able to be controlled. Obviously this is a bad thing to happen. We want our input devices to always work with the current ship or any ship that may be current in the infinite future. In order to make this happen, we need to be polymorphic in our ship/input device relationship.

Say we have two types of ships, one called Attacker and one called Explorer. Besides looking different and doing different things when activated they also move differently. When the Attacker "Thrusts" it moves very quickly so as to get to its target faster. When the Explorer "Thrusts" it moves slowly so as to not disturb what it is exploring. Even though they move differently, the way they are told to move is the same. That is, I tell both ships to move, or to "Thrust", and they then move in their own special way.

Thinking back on the notion of inheritance, what might we conclude about this relationship? They both can move but they move differently. They are also ships and might also share other commonalities. What can we do? We can create a a superclass called Ship.

But why do we want to do this? The answer is simple, both an Attacker and an Explorer are ships. Being ships they both share commonalities, i.e. the ability to move. By creating a superclass Ship and subclassing off of it we allow all ships (Attackers, Explorers, etc.) the ability to move, and to move in their own special way. More simply put, all Ships can move, but only an Attacker or Explorer knows how to move.

In effect, what we have just done is to create a polymorphic interface for all objects to manipulate any of our ships with. What I mean by polymorphic interface is that any object who has a reference to a ship (Attacker, Explorer or any other subclass we might ever create) knows how to manipulate it. A simpler way to state this is: Since I know how to manipulate one I know how to manipulate them all. More specifically, if I know how to manipulate a Ship I know how to manipulate an Attacker or an Explorer.

Since we want to insure that no matter what type of Ship we make current our input device will know how to manipulate it, we can employ this type of reasoning when we design our input device/ship relationship. Listing what we know so far:

Getting to the bottom line, instead of having our input device explicitly manipulate an Attacker or an Explorer we have it manipulate a Ship. This way, no matter what type of ship is current our input device will always be able to manipulate it.

By utilizing polymorphism to add extensibility to our designs gives us a lot of freedom to expand our programs. In the future when we want to add more functionality to our program the process becomes better facilitated and easier to understand. Perhaps more importantly, by creating this extensible interface we allow future programmers of our system to better add functionality by not confusing the design and our design intentions. Extensibility and polymorphism are two tools which work well together and allows us to create good, reusable designs.


This page was last updated by Shoe on 03/03/98.
Comments or suggestions, should be sent to: ahs@cs.brown.edu
Space is copyright 1996-1998 by Andrew H. Schulak