ITEC120-ibarland (incl. office hrs)—info—lectures—labs—hws—java.lang docs—java.util docs
lab week 15: inheritance; Unit testing
Work on this lab with a partner.
This lab will be checked off.
If you don't check it off today, you can check it off at the start
of lab on Friday
(but only in the first few minutes, as we'll have a separate task
on Friday's lab).
Our hw07 used two interfaces: IO, and Describable.
However, there was a difference between these two interfaces:
-
Different IO implementations don't really share
any code (say, TextIO and GuiIO);
the interface just describes behavior.
This is good.
-
The situation is more annoying with Describable; each
class implementing Describable was full of the same
code which did the same task for the same reason.
This repetition is annoying; an interface is not
so appropriate here.
In this lab, we'll convert Describable to
a class and have other classes inherit from it.
-
Make a copy of hw07 to play with for this lab session
(either your copy, or yoru partner's, or from
the posted solution (.jar)
-
Delete the interface Describable.
To replace it, make a class Describable
(which will be empty for the moment, but we'll add back the
methods getName, getDescription below).
Question: Should Describable be an abstract class?
-
Change “Room implements Describable”
to “Room extends Describable”
(and similarly for Treasure).
Your classes Room and Treaure
should still compile.
-
Make sure your Treasure and
Room classes still runs all their test cases.
Why doesn't TextIO compile, at the moment?
(This is okay; we'll fix this in the next step.)
Note that if your BlueJ window has an arrow from Explorer to TextIO,
then
trying to compile Explorer will work successfully,
but it will also try
to compile
TextIO
which will make BlueJ beep.
-
Now, the main step:
Rewrite your code so that
you gather all the repeated code which Describables have
in common, and collect it into that class.1
- Move the repeated fields into the superclass. (They should still
be private.)
Delete the fields from the subclasses; we don't want them repeated.
- Similarly, move the repeated methods
into the superclass. (They should still
be public.)
Delete the methods from the subclasses; we don't want them repeated.
-
Write the constructor for Describable.
Then,
make sure your constructors for Room and Treasure
start with a call to
super(…, …)
(that is, to the constructor for the superclass Describable).
- By the way, if you have Explorer extends Describable
(which is what the posted solution has),
then note that an Explorer's description is
“an intrepid explorer”.
-
Make sure all your test cases still work, after this re-write.
(This time, even TextIO should compile and test.)
-
(Optional, but you'll need to understand the concept for the final:)
For the last step, we can go beyond what we did before:
Override the getDescription for Treasures,
so that the Treasure's weight is included in parentheses,
after the primary description.
That is,
(new Treasure("Egg", "hard boiled", 0.5)).getDescription()
// Returns: "hard boiled [0.5lbs]"
(new Room("Davis 225", "full of happiness")).getDescription()
// Returns: "full of happiness"
|
Warning (confession):
The provided code testTreasure
didn't test getDescription() (only toString);
go ahead and test getDescription separately.
(Note how there is different code being called for these
two methods.)
ITEC120-ibarland (incl. office hrs)—info—lectures—labs—hws—java.lang docs—java.util docs
Dec.08 (Fri) — the last 120 lesson!
Unit Testing
Work through
the following
Unit Testing
tutorial.
You don't need to use their class Student for tests;
you can instead test the getters/setters for your class Treasure,
say.
…
When done with the tutorial,
be sure to double-click on the unit-test file which
BlueJ creates for you,
and look at the internal code.
This is important because other IDEs
may not have BlueJ's “record” feature,
but they do provide other tools to help you write
the unit-testing code you see.
Note that writing unit tests for
Explorer's grab are a bit more involved:
you need to first create an Explorer and a Room
with some Treasures;
then after calling grab you need to assert
something about the contents of the Explorer's pockets
as well as the Room's list of Treasures.
1
This is called “refactoring” the code.
Compare to algebra where factoring means going from
x⋅y-x⋅4 to x⋅(y-4),
avoiding the extra multiplication.
Similar, we are factoring out the common bits of code which were
distributed over the files.
…Why refactoring code? That term means, more generally,
taking code and making it better-organized,
without changing how it behaves.
back
ITEC120-ibarland (incl. office hrs)—info—lectures—labs—hws—java.lang docs—java.util docs