Lab: Experimenting with Accessibility/Visibility
Instructions:
Answer as many of the following questions as you can during the lab period.
If you are unable to complete the assignment during the lab period it
is strongly recommended that you complete it on your own.
Getting Ready:
Before going any further, you should:
-
Make a directory for this lab.
-
Setup your development environment.
-
Download the following files:
to the appropriate directory/directories. (In most browsers, the
easiest way to do this is by right-clicking on each of the links
above.)
1. Review:
This part of the lab is a review of material from earlier in the semester.
-
Compile all of the classes and execute
Driver
.
-
What output was generated?
Contains 18 word(s).
George is a little monkey, and all monkeys are curious. But no monkey is as cur
ious as George.
-
In
Driver
, don't change the declaration of the
variable named doc
but change the line containing
doc = new Document(text);
to doc = new
String(text);
.
-
Compile
Driver
.
-
What error was generated? Why?
Driver.java:24: incompatible types
found : java.lang.String
required: Document
doc = new String(text);
^
1 error
This error was generated because a String
object
(the right operand of the assignment operator)
is not a Document
(the left operand of the assignment operator).
-
In
Driver
, don't change the declaration of the
variable named doc
but change the line that now
contains doc = new String(text);
to doc = new
FormattedDocument(text);
.
-
Compile
Driver
.
-
What error was generated? Why?
Driver.java:24: cannot find symbol
symbol : constructor FormattedDocument(java.lang.String)
location: class FormattedDocument
doc = new FormattedDocument(text);
^
1 error
The FormattedDocument
class does not have a constructor
with a single String
parameter.
-
Does the parent class of
FormattedDocument
have
a constructor
with a single String
parameter?
Yes.
-
Does the
FormattedDocument
class inherit
constructors from its parent?
No. In Java, constructors are not inherited and this is a good example
of why they aren't. A FormattedDocument
cannot do its
job without knowing the maxWidth
so it doesn't make
sense to allow someone to construct a FormattedDocument
without one.
-
In
Driver
, Don't change the declaration of the
variable named doc
but change the line that now
contains doc = new FormattedDocument(text);
to doc = new FormattedDocument(text, 20);
.
-
Compile
Driver
.
-
Why did it compile even though there appear to be
incompatible types?
It compiles because a FormattedDocument
(the right operand of the assignment operator) "is a"
Document
(the left operand of the assignment operator) since
FormattedDocument
extends Document
.
-
Execute the driver.
-
What output was generated?
This document has 18 words and at least 4 lines.
George is a little
monkey and all
monkeys are curious
But no monkey is as
curious as George
-
Why were the
getDescription()
and getText()
methods in the FormattedDocument
class used even though
doc
is declared to be a Document
?
doc
behaved like a FormattedDocument
even though it was declared to be a Document
because
doc
contains a reference to a
FormattedDocument
. We will explore these kinds of
issues more fully when we discuss polymorphism.
-
The
getText()
method in the FormattedDocument
class contains the line temp = super.getText();
. Explain
this line of code.
The getText()
method in the
FormattedDocument
class is calling the method
getText()
method in the Document
class.
-
Replace the line
temp = super.getText();
in the
FormattedDocument
class with the
line temp = getText();
.
-
Compile
FormattedDocument
and execute Driver
.
-
What output/error message was generated and why?
java.lang.StackOverflowError
at FormattedDocument.getText(FormattedDocument.java:77)
This (run-time) error was generated becase the getText()
method calls itself over and over, never stopping. This is called
an infinite recursion.
2. Accessibility/Visibility Basics:
In this part of the lab you will experiment with some of the basics
of accessibility/visibility concepts.
-
Compile
Counter.java
-
What error was generated?
Counter.java:13: cannot find symbol
symbol : variable i
location: class Counter
return i;
^
-
Why was this error generated?
Because i
has block scope and is not accessible outside
of the for
statement.
-
Add the following line to the top of the
Counter
class.
public int i;
-
Compile
Counter.java
-
Why was no error generated?
Because the i
in the return
statement
refers to the attribute, not the local variable.
-
Change the declaration of the attribute
i
so that it is now
private.
-
Compile
Counter.java
-
Why was no error generated?
Because the attribute i
is accessible to all objects of the
Counter
class.
-
Assuming no other changes, what value will be returned by the
firstNonNull()
method when it is called.
0
-
Why?
Because the value of the attribute i
is 0.
-
Delete the declaration of the attribute
i
.
-
Add the following line to the top of the
firstNonNull()
method without making any other changes.
private int i;
-
Compile
Counter.java
-
What error was generated?
Counter.java:7: illegal start of expression
private int i;
^
-
Why was this error generated?
Because a local variable can not have an accessibility modifier.
-
Fix
firstNonNull()
so that it works propery.
-
What changes did you make?
I removed private
from the declaration of the local
variable i
and removed the declaration of i
from the for
statement.
-
Compile
Counter.java
to make sure you have didn't
make any syntax errors.
-
Remove the initialization of
i
from the for
statement (but leave the semi-colon).
-
Compile
Counter.java
,
-
What error was generated?
Counter.java:9: variable i might not have been initialized
for (; i<values.length; i++)
^
3. Some Accessibility/Visibility Examples:
In this part of the lab you will experiment with changing the
accessibility/visibility of attributes and methods.
-
Make the accessibility of the
getDelimiters()
method in the Document
class private
.
-
Compile only the
Document
class.
-
Why are no error messages generated?
Because private methods are still
available/visible within the class.
-
Compile only the
FormattedDocument
class.
-
What error is generated and why?
FormattedDocument.java:78: getDelimiters() has private access in Document
delim = super.getDelimiters();
This error is generated because
the getDelimiters()
method is no longer
available by any other
classes, including derived classes.
-
Make the
getDelimiters()
method in the Document
class protected
.
-
Compile all of the classes.
-
Why are no errors generated?
The getDelimiters()
method in the Document
class is now accessible by subclasses and no other classes use it.
-
What's the difference between the
public
version
and the protected
version?
Which is better? Why?
The first is visible to all classes, the second is visible
only to subclasses.
In this case it is probably better for it to be
protected. First, it is
hard to imagine why any class other than an ancestor would
need to get the delimiters. Second, when it is public the
API for the class is more complicated (i.e., there are
more methods to try and understand).
-
Perform the same experiments with the
getWordCount()
method.
-
In this case, which version is better? Why?
In this case, the getWordCount()
method is likely
to be used by a whole variety of classes. Hence, it makes
sense for it to be public.
-
Change the accessibility of the
delimiters
and
text
attributes in the Document
class
to protected.
-
What changes can you now make to the
FormattedDocument
class? (Hint: Think about how
the FormattedDocument
class accesses these attributes.)
You no longer need to use super.getText()
and
super.getDelimiters()
in the subclass. Instead,
you can directly use text
and delimiters
.
-
Do you like these changes? Why or why not?
This is a hard one. At first glance it seems a lot simpler to
use the attributes directly rather than the accessor methods.
However, in subsequent labs we will see how this can get
you into trouble.
-
Now that the
delimiters
attribute is protected
,
do you still need the getDelimiters()
method?
Certainly not the protected version.
-
Should either the
getDescription()
or
getText()
methods in the Document
class be protected? Why or why not?
Definitely not since they are used by other classes.