📄 java2.txt
字号:
public class AnotherFinalClass {
public static final int aConstantInt = 123;
public final String aConstantString = "Hello world!";
}
Local variables (those inside blocks of code surrounded by
braces, for example, in while or for loops) can't be declared
final.
Finalizing Methods
Finalized methods are methods that cannot be overridden; that
is, their implementations are frozen and cannot be redefined in
subclasses.
public class ClassWithFinalMethod {
public final void noOneGetsToDoThisButMe() {
. . .
}
}
The only reason to declare a method final is efficiency.
Normally, method signatures and implementations are matched up
when your Java program runs, not when it's compiled. Remember
that when you call a method, Java dynamically checks the current
class and each superclass in turn for that method's definition.
Although this makes methods very flexible to define and use,
it's not very fast.
If you declare a method final, however, the compiler can then
"in-line" it (stick its definition) right in the middle of
methods that call it because it "knows" that no one else can
ever subclass and override the method to change its meaning.
Although you might not use final right away when writing a
class, as you tune the system later, you may discover that a few
methods have to be final to make your class fast enough. Almost
all your methods will be fine, however, just as they are.
If you use accessor methods a lot (as recommended), changing
your accessor methods to be final can be a quick way of speeding
up your class. Because subclasses will rarely want to change the
definitions of those accessor methods, there's little reason
those methods should not be final.
The Java class library declares a lot of commonly used methods
final so that you'll benefit from the speed-up. In the case of
classes that are already final, this makes perfect sense and is
a wise choice. The few final methods declared in non-final
classes will annoy you-your subclasses can no longer override
them. When efficiency becomes less of an issue for the Java
environment, many of these final methods can be "unfrozen"
again, restoring this lost flexibility to the system.
Note
Private methods are effectively final, as are all methods
declared in a final class. Marking these latter methods
final (as the Java library sometimes does) is legal, but
redundant; the compiler already treats them as final.
It's possible to use final methods for some of the same
security reasons you use final classes, but it's a much
rarer event.
Abstract Classes and Methods
Whenever you arrange classes into an inheritance hierarchy, the
presumption is that "higher" classes are more abstract and
general, whereas "lower" subclasses are more concrete and
specific. Often, as you design hierarchies of classes, you
factor out common design and implementation into a shared
superclass. That superclass won't have any instances; its sole
reason for existing is to act as a common, shared repository for
information that its subclasses use. These kinds of classes are
called abstract classes, and you declare them using the abstract
modifier. For example, the following skeleton class definition
for the Fruit class declared that class to be both public and
abstract:
public abstract class Fruit {
...
}
Abstract classes can never be instantiated (you'll get a
compiler error if you try), but they can contain anything a
normal class can contain, including class and instance variables
and methods with any kind of protection or finalization
modifiers. In addition, abstract classes can also contain
abstract methods. An abstract method is a method signature with
no implementation; subclasses of the abstract class are expected
to provide the implementation for that method. Abstract methods,
in this way, provide the same basic concept as abstract classes;
they're a way of factoring common behavior into superclasses and
then providing specific concrete uses of those behaviors in
subclasses.
Abstract classes are classes whose sole purpose is to provide
common information for subclasses. Abstract classes can have no
instances.
Abstract methods are methods with signatures, but no
implementation. Subclasses of the class which contains that
abstract method must provide its actual implementation.
Like abstract classes, abstract methods give you the ability to
factor common information into a general superclass and then
reuse that class in different ways.
The opposite of abstract is concrete: Concrete classes are
classes that can be instantiated; concrete methods are those
that have actual implementations.
Abstract methods are declared with the abstract modifier, which
usually goes after the protection modifiers but before either
static or final. In addition, they have no body. Abstract
methods can only exist inside abstract classes; even if you have
a class full of concrete methods, with only one abstract method,
the whole class must be abstract. This is because abstract
methods cannot be called; they have no implementation, so
calling them would produce an error. Rather than worry about
special-case abstract methods inside otherwise concrete
instances, it's easier just to insist that abstract methods be
contained only inside abstract classes.
Listing 15.2 shows two simple classes. One, appropriately called
MyFirstAbstractClass, has an instance variable and two methods.
One of those methods, subclassesImplementMe(), is abstract. The
other, doSomething(), is concrete and has a normal definition.
The second class is AConcreteSubclass, which is a subclass of
MyFirstAbstractClass. It provides the implementation of
subclassesImplementMe(), and inherits the remaining behavior
from MyFirstAbstractClass.
Note
Because both these classes are public, they must be defined
in separate source files.
Listing 15.2. Two classes: one abstract, one concrete.
1:ipublic abstract class MyFirstAbstractClass {
2: int anInstanceVariable;
3:p
4: public abstract int subclassesImplementMe(); // note no definition
5:
6: public void doSomething() {
7: . . . // a normal method
8: }
9:}
10:
11:public class AConcreteSubClass extends MyFirstAbstractClass {
12: public int subclassesImplementMe() {
13: . . . // we *must* implement this method here
14: }
15:}
Here are some attempted uses of these classes:
Object a = new MyFirstAbstractClass(); // illegal, is abstract
Object c = new AConcreteSubClass(); // OK, a concrete subclass
Using an abstract class with nothing but abstract methods-that
is, one that provides nothing but a template for behavior-is
better accomplished in Java by using an interface (discussed
tomorrow). Whenever a design calls for an abstraction that
includes instance state and/or a partial implementation,
however, an abstract class is your only choice.
Summary
Today you have learned how variables and methods can control
their visibility and access by other classes via the four Ps of
protection: public, package, protected, and private. You have
also learned that although instance variables are most often
declared private, declaring accessor methods allows you to
control the reading and writing of them separately. Protection
levels allow you, for example, to separate cleanly your public
abstractions from their concrete representations.
You have also learned how to create class variables and methods,
which are associated with the class itself, and how to declare
final variables, methods, and classes to represent constants and
fast or secure methods and classes.
Finally, you have discovered how to declare and use abstract
classes, which cannot be instantiated, and abstract methods,
which have no implementation and must be overridden in
subclasses. Together, they provide a template for subclasses to
fill in and act as a variant of the powerful interfaces of Java
that you'll study tomorrow.
Q&A
Q: Why are there so many different levels of protection in
Java?
A: Each level of protection, or visibility, provides a
different view of your class to the outside world. One
view is tailored for everyone, one for classes in your
own package, another for your class and its subclasses
only, one combining these last two and the final one
for just within your class. Each is a logically
well-defined and useful separation that Java supports
directly in the language (as opposed to, for example,
accessor methods, which are a convention you must
follow).
Q: Won't using accessor methods everywhere slow down my
Java code?
A: Not always. As Java compilers improve and can create
more optimizations, they'll be able to make them fast
automatically, but if you're concerned about speed, you
can always declare accessor methods to be final, and
they'll be just as fast as direct instance variable
accesses.
Q: Are class (static) methods inherited just like instance
methods?
A: No. static (class) methods are now final by default.
How, then, can you ever declare a non-final class
method? The answer is that you can't! Inheritance of
class methods is not allowed, breaking the symmetry
with instance methods.
Q: Based on what I've learned, it seems like private
abstract methods and final abstract methods or classes
don't make sense. Are they legal?
A: Nope, they're compile-time errors, as you have guessed.
To be useful, abstract methods must be overridden, and
abstract classes must be subclassed, but neither of
those two operations would be legal if they were also
private or final.
Q: What about the transient modifier? I saw that mentioned
in the Java Language Specification.
A: The transient modifier is reserved by the designers of
Java for use in future versions of the Java language
(beyond 1.0.2 and 1.1); it will be used to create
persistent object store systems (the ability to save a
set of classes and objects and restore their state
later on). It, like other modifiers such as byvalue,
future, and generic, are not currently used but are
reserved words in the language.
Q: I tried creating a private variable inside a method
definition. It didn't work. What did I do wrong?
A: Nothing. All the modifiers in this chapter, when you
can use them with variables, only apply to class and
instance variables. Local variables-those that appear
inside the body of a method or loop-cannot use any of
these modifiers.
----------
Day 16
Packages and Interfaces
by Laura Lemay and Charles L. Perkins
CONTENTS
* Programming in the Large and Programming in the Small
* What Are Packages?
* Using Packages
* Full Package and Class Names
* The import Command
* Name Conflicts
* A Note About CLASSPATH and Where Classes Are Located
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -