Java Tips
Object-Oriented Programming
-
No explicit cast needed for upcasting, but explicit
cast needed for downcasting.
-
Defining your class as implementing an interface marks
objects of that class as an instance of that interface.
-
An abstract method cannot (obviously) be final.
-
An abstract method cannot be static because
static
methods cannot be overridden.
-
An instance method can be both protected and abstract.
A static method can be protected.
-
Before Java runtime clones an object, it checks to see if
the object’s class implements the Cloneable interface. If it does, the
clone()
method returns a clone of the object. If not, the clone() method
throws a CloneNotSupportedException.
-
The clone method is protected, so an object can only request
a clone of another object which is either in the same package or which
it inherits from. (i.e. standard meaning of protected)
-
The JVM does not call an object’s constructor when you clone
the object.
Keywords
-
Classes can be modified from their default state using any
of the three keywords: public, abstract, and final. So, can’t
have a static class, only static methods.
-
A final variable is a constant, and a final method cannot
be overridden.
-
A synchronised method can belong to an object or to a class.
-
Only one public class per file.
-
package statement must come first in file and must be followed
by any import statements.
-
An identifier is an unlimited-length sequence of Java
letters and Java digits, the first of which must be a Java letter.
Java letters include _ and $. Digits include 0..9.
Constructors
-
The JVM does not call an object’s constructor when
an object is cloned.
-
Constructors never return a value. If you do specify a return
value, the JVM will interpret your intended constructor as a method.
-
If a class contains no constructor declarations, then a default
constructor that takes no arguments is supplied. This default constructor
invokes the no-args superclass constructor, i.e. calls super();
-
If, in a constructor, you do not make a direct call to super
or
this
(with
or without args) [note: must be on the first line] then
super(no
args) will first be invoked then any code in the constructor will be
executed. See constructors.jpr project.
-
A call to this in a constructor must also be on the
first line. Note: can’t have an explicit call to super followed
by a call to this in a constructor - only one direct call to another
constructor is allowed.
Memory and Garbage Collection
-
As soon as you lose the reference to an object, that object
becomes eligible for garbage collection.
-
Setting your object reference to null makes it a candidate
for garbage collection.
-
You can directly invoke the garbage collector by getting
an object which represents the current runtime and invoking that object’s
gc()
method (see p.95 of Exam Guide).
-
Can’t predict when garbage collection will occur, but it
does run whenever memory gets low.
-
If you want to perform some task when your object is about
to be garbage collected, you can override the java.lang.Object method called
finalize().
This
method is declared as protected, does not return a value, and throws a
Throwable object, i.e. protected void finalize() throws Throwable.
-
Always invoke the superclass’s finalize() method if
you override finalize().
-
The JVM only invokes finalize() once per object.
Since this is the case, do not resurrect an object in finalize as when
the object is finalized again its finalize() method will not be
called. Instead you should create a clone of the object if you must bring
the object back to life.
-
Remember that Java passes method parameters by value and
not by reference. Obviously then, anything that happens to a primitive
data type inside a method does not affect the original value in the calling
code. Also, any reassignment of object references inside a method has no
effect on the objects passed in.
Data Types and Values
-
Ranges for primitive data types are as follows:-
Data
Type |
Range
of Values |
|
byte |
-27.. 27-1
|
signed integer
|
short |
-215.. 215-1
|
signed integer
|
int |
-231.. 231-1
|
signed integer
|
long |
-263.. 263-1
|
signed integer
|
float |
32 bit
|
signed floating point
|
double |
64 bit
|
signed floating point
|
char |
16 bit
|
Unicode character
|
boolean |
either true or false
|
|
-
To specify an octal (base 8) number, put a leading ‘0’ in
front of i
-
To specify a hexadecimal (base 16) number, put a leading
‘0x’ in front of it.
-
By default, integer values are of type int. However,
you can force an integer value to be a long by placing an ‘L’ after it.
-
By default, floating point values are of type double.
However, you can force a floating-point value to be a float by placing
an ‘F’ after it.
-
Java sets each element in an array to its default value when
it is created. Default object value is null, default integer value
is 0, default boolean value is false, default floating point value
is 0.0, default char value is ‘\u0000’.
-
Arrays are objects allocated at runtime, so you can use a
variable to set their length.
-
First element in an array is at index 0 and last element
is at length-1. length is a special array variable (not a
method, so don’t need round brackets after it).
-
Can only use curly braces in array initialisation when array
is actually declared, i.e. can’t declare the array on one line then initialise
it with curly braces on line below.
-
ASCII characters are all found in the range ‘\u0000’ to ‘\u00ff’
-
The default value for any class variable or instance variable
declared as a char is ‘\u0000’.
Operators
-
>> is right shift keep the sign, >>> is right shift don’t
keep the sign.
-
& and | can be used with both integral and boolean types.
If used with integers the result is integral. If used with booleans, both
operands are evaluated, even when the result of the operation can be determined
after evaluating only the left operand.
-
&& and || are used with boolean operands only. The
right operand is not evaluated if the result of the operation can be determined
after evaluating only the left operand.
-
The equals() method (defined at the ‘highest’ level
as a method of Object) is used to test the value of an object. The == operator
is used to test the object references themselves.
-
By default, equals() returns true only if the objects
reside in the same memory location, i.e. if the object references are equal.
So, by default, equals() and == do the same things. This will be the
case for all classes that do not override equals().
-
String, Wrappers (including Integer, Long, Float, Double,
Character and Boolean), BitSet, Date and File classes all override equals()
so that the value true is returned if the values are equal.
-
The + and += operators are overloaded for Strings.
-
Dividing an integer by 0 is illegal and would cause Java
to throw an ArithmeticException. Floating point numbers have values
for infinity and not-a-number, so using arithmetic operators on floating
point numbers never results in an exception.
Control Flow
-
A loop counter is usually an integer, however it could also
be a floating point number - incrementing by 1.0
-
Breaking to a label means that the loop at the label is terminated.
Any outer loop will keep iterating.
-
In contrast, a continue to a label continues execution with
the next iteration of the labelled loop.
-
The expression for an if and while statement must be a
Boolean.
-
The expression in a switch statement must be an int or
a char.
-
A default statement in a switch is optional.
-
A case block will fall through to the case block which follows
it, unless the last statement in a case block is a throw, return
or break.
-
As with if statements, for and while loops, it is possible
to nest switch statements.
-
Any line of code can be labelled BUT can only do a
labelled continue to a loop, and can only do a labelled break to a loop
or to an enclosing statement.
Exceptions
-
It is possible to have multiple catch blocks in a try-catch-finally.
The finally block is optional.
-
A catch block must always be associated with a try block,
i.e. can’t have a catch block by itself or with a finally block.
-
A finally block must always be associated with a try block,
i.e. can’t have a finally block by itself or with a finally block.
-
With multiple catch blocks, the type of exception caught
must progress from the most specific exception that you wish to catch to
the superclasses for these exceptions. (Makes sense!)
-
Methods must declare any exception which they throw.
-
Invoking a method which declares it throws exceptions is
not possible unless either the code is placed in a try-catch, or the calling
method declares that it throws the exceptions, i.e. checked exceptions
must be caught or rethrown. If the try-catch approach is used, then the
try-catch must cope with all of the exceptions which a method declares
it throws.
-
You can list more than one exception in the throws clause
if you separate them with commas.
-
RuntimeException and its subclasses are unchecked
exceptions.
-
Unchecked exceptions do not have to be caught.
-
All Errors are unchecked.
-
You should never throw an unchecked exception in your own
code, even though the code will compile.
-
You cannot use a try block on its own. It must be accompanied
by a following catch or finally (or both).
-
Code in a finally block will always be executed, whether
an exception is thrown or not and whether any exception thrown is caught
or not. Only terminating the program will stop the finally code from being
executed.
-
A method can only throw those exceptions listed in its throws
clause, or subclasses of those exceptions.
-
A method can throw any unchecked exception, even if it is
not declared in its throws clause.
-
When you override a method, you must list those exceptions
that the override code might throw. You can list only those exceptions,
or subclasses of those exceptions, that are defined in the method definition
you are inheriting from, i.e. you cannot add new exception types to those
you inherit. You can choose to throw a subset of those exceptions listed
in the method’s superclass, however, a subclass further down the hierarchy
cannot then re-list the exceptions dropped above it.
Methods
-
If you define more than one method with the same name in
the same class, Java must be able to determine which method to invoke based
on the number and types of parameters defined for that method.
-
The compiler will complain if you have two methods with identical
signatures exception for the return type and/or the exceptions thrown,
i.e. can’t overload based on return type and/or exceptions thrown.
-
Determining which methods will be invoked with integer params
- see p.195 of the Exam Guide.
-
It is possible to declare an inherited method abstract.
-
Obviously, it is not possible to override a final
method.
-
A subclass may make an inherited method synchronized,
or it may leave off the synchronized keyword so that its version is not
synchronized. If a method in a subclass is not synchronized but the method
in the superclass is, the thread obtains the monitor for the object when
it enters the superclass’s method.
-
It is possible to declare an inherited method as abstract,
but then there is no way to get to the behaviour in the hierarchy above
the abstract declaration.
-
Return types must match the overriden method in the superclass
exactly. The parameter types must match those in the superclass exactly,
i.e. in the same order. If this is not the case, then the superclass’s
method is not overridden. Compiler will not complain, however, unless
exactly the same signature except for return type (or exceptions thrown
- see earlier).
-
You cannot make a method in a subclass more private than
it is defined in the superclass, ‘though you can make it more public.
-
Coercion of arguments only happens with overloading, not
overriding.
-
It is perfectly legal to have two different instance variables
with the same name if they are defined in different classes where one class
inherits from the other.
-
Which variable is accessed depends on the type of object
reference which the variable was declared to hold. Which method gets
invoked depends on the underlying object. See p.106 Q1 & p.201
of Exam Guide.
-
A native method does not have a body, or even a set
of braces, e.g. public native void method();
-
A native method cannot be abstract.
-
A native method can throw exceptions.
Math and String Classes
-
ceil() returns the next highest integer (expressed
as a double)
Method
call |
Returns |
ceil(9.01) |
9.0
|
ceil(-0.1) |
0.0
|
ceil(100) |
100.0
|
-
round() returns the closest integer (expressed as
an int if the parameter was a float, or a long if the parameter was a double)
Method
call |
Returns |
round(9.01) |
9
|
round(9.5) |
10
|
round(-9.5) |
-9
|
round(-0.1) |
0
|
round(100) |
100
|
-
random() returns a random number, a double, between
0.0 and 1.0
-
sqrt() takes a double and returns a double. If the
argument is NaN or <0, the result is NaN.
-
sin(), cos() and tan() all take a double
and return a double.
-
All objects respond to toString(), which you can override
to return a String representation of your object.
-
String objects have the following methods: length(), toUpperCase(),
toLowerCase(), equals(), equalsIgnoreCase(), charAt(), indexOf(), lastIndexOf(),
substring(), toString() and trim().
-
There are four versions of indexOf()
Arguments |
Results |
(int ch) - works if you put a
char in! |
Finds the first occurrence of
this character |
(int ch, int fromIndex) |
Finds the first occurrence of
this character starting from fromIndex |
(String substring) |
Finds the start of this substring |
(String substring, int fromIndex) |
Finds the start of this substring
searching from fromIndex |
-
There are four versions lastIndexOf() - as above table
but, in each method, finding the last index rather than the first index.
-
First character in a String is at position 0, last character
is at position length()-1
-
There are two versions of substring()
Arguments |
Results |
(int startIndex) |
Returns a substring starting with
startIndex and extending to the end of the String |
(int startIndex, int endIndex) |
Returns a substring starting with
startIndex and extending to (but not including) endIndex |
-
For a StrintoString() returns itself - the same object
reference (obviously pointing to the same object) that was used to invoke
the method.
-
trim() returns a new String object that cuts off any
leading and trailing whitespace for the String for which it was invoked.
-
Java considers "whitespace" to be any character with a code
less than or equal to ‘\u0020’ which is the space character.
Input/Output
-
InputStream and OutputStream are abstract classes.
-
FileInputStream and FilterInputStream both inherit directly
from InputStream.
-
FileOutputStream and FilterOutputStream both inherit directly
from OutputStream.
-
DataInputStream inherits directly from FilterInputStream.
-
DataOutputStream inherits directly from FilterOutputStream.
-
When you create a Filter stream, you must specify the stream
to which it will attach.
-
A Filter stream processes a stream of bytes in some way.
By "chaining" any number of Filter streams, you can add any amount of processing
to a stream of bytes.
-
DataInputStream, DataOutputStream and RandomAccessFile know
how to work with Java data types because they implement the DataInput and
DataOutput interfaces, whereas FileInputStream and FileOutputStream know
only how to work with individual bytes.
-
RandomAccessFile implements both DataInput and DataOutput
methods - RandomAccessFile objects can read from and write to files.
-
The File class is not used to create files. Can create
a file using an instance of class RandomAccessFile and FileOutputStream.
-
To test if a File object refers to an existing file, you
can invoke exists() which returns true or false. The File methods
canRead()
and canWrite() return boolean values that indicate whether the application
can read from or write to the file. (Note: applets can’t write to a file.)
-
Can use File methods to make a permanent change to the file
system. For example, you can call delete() or rename(). For
rename(),
need to supply a File object which embodies the new name.
-
You can create a directory using the File class. The method
mkdir()
does this.
-
It is possible to navigate the filing system using the File
class. Methods getParent(), getPath() and getName() are provided,
and also getAbsolutePath().
-
The method getAbsolutePath() returns the name of the
current user directory (the full pathname included) with the file name
concatenated. See Practice Exam 1 Q.45
-
Creating a FileOutputStream object creates the appropriate
file. If the file already exists, FileOutputStream replaces it (unless
the FileOutputStream object is created using the constructor which takes
a String and a boolean - see later)
-
Upon creation of a RandomAccessFile object, need to supply
a file object plus a mode. Alternatively, can supply a filename plus a
mode.
-
Valid modes for RandomAccessFile are "r" and "rw".
-
Constructors for FileInputStream: one takes a String, one
takes a File, one takes a FileDescriptor
-
Constructors for FileOutputStream: one takes a String, one
takes a File, one takes a FileDescriptor, one takes a String and
a boolean (which indicates whether or not to append).
-
Constructors for FilterInputStream: one only, which takes
an InputStream
-
Constructors for FilterOutputStream: one only, which takes
an OutputStream
-
See Chapter 11 Review Questions for io stuff - very useful.
Threads
-
A Java program runs until the only threads left running are
daemon threads.
-
A Thread can be set as a user or daemon thread when it is
created.
-
In a standalone program, your class runs until your main()
method exists - unless your main() method creates more threads.
-
You can initiate your own thread of execution by creating
a Thread object, invoking its start() method, and providing the
behaviour that tells the thread what to do. The thread will run until its
run()
method exists, after which it will come to a halt - thus ending its life
cycle.
-
The Thread class, by default, doesn’t provide any behaviour
for run().
-
There are two ways to provide the behaviour for a thread
-
Subclass the thread and override the run() method
- see p.253 of Exam Guide.
-
Implement the Runnable interface and indicate an instance
of this class will be the thread’s target.
-
A thread has a life cycle. Creating a new Thread instance
puts the thread into the "new thread" state. When the start() method
is invoked, the thread is then "alive" and "runnable". A thread at this
point will repond to the method isAlive() by returning true.
-
The thread will continue to return true to isAlive()
until it is "dead", no matter whether it is "runnable" or "not runnable".
-
If 2 threads are alive, with the same highest priority, the
JVM switches between them. The JVM will switch between any number of threads
with the same highest priority.
-
The priority numbers for threads falls between the range
of Thread.MIN_PRIORITY and Thread.MAX_PRIORITY.
-
The default thread priority is Thread.NORM_PRIORITY.
-
New threads take on the priority of the thread that spawned
them.
-
You can explicitly set the priority of a thread using setPriority(),
and you can get the priority of a thread using getPriority(). There
is no constructor for thread which takes a priority.
-
The JVM determines the priority of when a thread can run
based on its priority ranking, but this doesn’t mean that a low priority
thread will not run.
-
The currently executing thread can yield control by invoking
yield().
If you invoke yield(), Java will pick a new thread to run. However,
it is possible the thread that just yielded might run again immediately
if it is the highest priority thread.
-
There are 3 types of code that can be synchronized:
class methods, instance methods, any block of code within a method.
-
Variables cannot take the synchronized keyword.
-
Synchronization stays in effect if you enter a synchronized
method and call out to a non-synchronized method. The thread only gives
up the monitor after the synchronized method returns.
-
Using a thread’s stop() method will make it die.
-
There are 3 ways to transition a thread between "runnable"
and "not runnable"
put it to sleep and wake it up |
(not on the test) |
pause it and resume it |
(not on the test) |
use the methods wait(), notify() and notifyAll()
- these are methods of class Object. wait() throws InterruptedException. |
|
-
The third method listed above allows communication between
the threads, whereas the other 2 methods don’t.
-
By using the methods wait(), notify() and notifyAll(),
any thread can wait for some condition in an object to change, and any
thread can notify all threads waiting on that object’s condition that the
condition has changed and that they should continue.
-
When a waiting thread pauses, it relinquishes the object’s
monitor and waits to be notified that it should try to reacquire it.
-
If you know you only have one thread waiting on a condition,
you can feel free to use notify(), otherwise you should use notifyAll().
The notifyAll() method wakes up all threads waiting to reacquire
the monitor for the object.
-
The reasons why a thread might be "alive" and "not runnable"
are as follows:
-
the thread is not the highest priority thread and so is not
able to get CPU time
-
the thread has been put to sleep using the sleep()
method (of class Thread. Throws InterruptedException)
-
the thread has been suspended using the suspend()
method
-
the thread is waiting on a condition because someone invoked
wait()
for the thread
-
the thread has explicitly yielded control by invoking yield()
Graphical User Interfaces
-
If you want to explicitly repaint a component, you should
not call paint() directly. Instead you should invoke your component’s
repaint()
method.
-
The repaint() method is overloaded. The no-args version
of repaint() does not cause your user interface to repaint right
away. In fact, when repaint() returns, your component has not yet
been repainted - you’ve only issued a request for a repaint(). There
is another version of repaint() that requests the component to be
repainted within a certain number of milliseconds.
-
The repaint() method will cause AWT to invoke a component’s
update()
method. AWT passes a Graphics object to update() - the same one
that it passes to paint(). So, repaint() calls
update()
which calls paint().
-
The Graphics object that AWT hands to update() and
paint()
is different every time the Component is repainted.
-
When Java repaints on its own, such as when the user resizes
an applet, the AWT does not invoke update() - it just calls paint()
directly.
-
The update() method does three things in this order:
-
clears the background of the object by filling it with its
background colour
-
sets the current drawing colour to be its foreground colour
-
invokes paint(), passing it the Graphics object received
-
Common graphics methods:
-
drawString() - takes a String, followed by x then
y co-ord of baseline for first char
-
drawLine() - takes x then y co-ords of starting point,
then x then y co-ords of end point
-
drawRect() / fillRect() - take 4 params - x
then y co-ords of top left corner, then width then height
-
drawOval() / fillOval() - take 4 params - x,
y, width, height and draw an oval inside corresponding rectangle
-
drawPolygon() / fillPolygon() - (int[] xpoints,
int[] ypoints, int npoints) - array of x co-ords then array of y co-ords
followed by the number of points to use
-
drawArc() / fillArc() - takes 6 params - x
then y co-ord of top left corner (of bounding rectangle of corresponding
oval), width then height of arc, then start angle (not really an angle,
more a position on the clock - 0 represents 3 o’clock), then number of
degrees to move along the arc. Last parameter can also be negative, if
you want to move in a clockwise direction round the arc.
-
The Image class does not provide a constructor for specifying
where an image will come from.
-
You can obtain an Image, typically by downloading it from
the Internet by specifying a URL. You can retrieve an image and obtain
an Image object by invoking an Applet method named getImage(). This
method takes a URL.
-
When the getImage() method returns, the data for the
image is not necessarily immediately available. The method returns right
away, even if the image resource is located over the Internet on a Web
server and must be downloaded.
-
When you invoke the Graphics method drawImage() the
image download begins. The object you specify as an ImageObserver keeps
the Java graphics system up-to-date on the state of the download. When
the ImageObserver sees that the download is complete, it notifies the graphics
system that it can draw the image in its entirety.
-
ImageObserver is an interface. The Component class implements
this interface, so any component (such as an Applet itself) can be used
as an ImageObserver.
-
TextArea takes rows then cols in constructor. If you type
in more text than can be displayed all at one, scrollbars appear automatically.
-
TextField takes only cols. A user may one type one
line into a TextField. No scrollbars appear if the line is too long to
be displayed, but can use arrow keys to move to beginning or end of text.
-
TextArea and TextField both inherit from TextComponent which
provides a setEditable() method.
-
For a variable width font, TextArea / TextField width is
based on average of letter widths.
-
Can populate a List using addItem() method.
-
As well as a no-args constructor and a constructor which
takes number of rows, List class also has a constructor which takes number
of rows followed by a boolean value which represents whether or not multiple
list item selections are allowed.
-
Java 1.0
-
Component methods for Java 1.0.2 - enable(), disable(),
show(), hide(), size(), resize(), setForeground(), setBackground().
-
enable() / disable() - make a component selectable
or not by the user.
-
size() / resize() - the size() method
retrieves the size of the Component as a Dimension object which has two
fields (width and height). The resize() method sets
the size of the Component. The method is overloaded - one version takes
a Dimension object and the other takes width and height directly as int
values.
-
show() / hide() - the show() method
makes a Component visible, the hide() method makes a Component invisible.
The show() method is overloaded so that you can supply a boolean
parameter to indicate whether to show the Component (if the parameter is
true).
-
A Frame is only visible when the show() method has
been invoked.
Java 1.1
-
Component methods for Java 1.1 - setEnabled(), getSize(),
setSize(), setVisible(), setForeground(), setBackground(). setEnabled()
replaces enable() / disable() and takes a boolean value.
getSize()
and setSize() replace size() / resize(). setVisible()
replaces
show() / hide() and takes a boolean value.
|
-
Java provides a Color class which defines many static constants
that contain instances of class Color already initialized to common colours.
To use red, for example, you can access Color.red. The Color class has
a constructor which takes three int values of red, green and blue so that
you can make up your own colour.
-
Each container has exactly one layout manager which
determines how to arrange the Components within a Container.
-
A layout manager is any class that implements the LayoutManager
interface. Java’s 5 layout managers all inherit directly from class Object,
but they implement the LayoutManager interface, which defines 5 abstract
methods:
-
addLayoutComponent()
-
layoutContainer()
-
minimumLayoutSize()
-
preferredLayoutSize()
-
removeLayoutComponent()
-
Instead of invoking the layout manager’s methods yourself,
Java’s default Container methods invoke them for you at the appropriate
times. These Container methods include add(), getMinimumSize(), getPreferredSize(),
remove() and removeAll() (these are all Java 1.1 methods).
-
Each type of container comes with a default layout manager.
Default for a Frame, Window or Dialog is BorderLayout. Default for
a Panel is FlowLayout().
-
A FlowLayout object arranges components left to right and
top to bottom, centering each line as it goes. The FlowLayout layout manager
is the only layout manager which allows components to be their preferred
size. If a container using a FlowLayout is resized, all of the components
inside it might need to be rearranged, and some might not be completely
visible.
-
A BorderLayout object arranges components according to the
directions "North", "South", "East" and "West". There’s also an area for
"Center" which includes any space left over from other regions.
-
Components are rarely allowed to be their preferred size
in a BorderLayout. BorderLayout stretches components. Stretches "North"
and "South" components horizontally. Stretches "East" and "West" components
vertically. Stretches "Center" components both horizontally and vertically.
-
If nothing is placed in "East" or "West", for example, then
the "Center" stretches all the way from the left edge of the Container
to the right edge.
-
Some components are stretchable and others are not. For example,
Button, Label and TextField are stretchable, whereas Checkbox is not.
-
GridLayout objects allow you to specify a rectangular grid
in which to place the components. Each cell in the grid is the same height
as the other cells, and each width is the same as the other cells. Components
are stretched both horizontally and vertically to fill the cell.
-
When a GridLayout object is first constructed, you must first
specify how many rows and how many columns the grid will have. Components
are added to the grid left to right and top to bottom. If more components
are added than there are columns, the GridLayout keeps the same number
of rows but adds the necessary number of columns.
-
You can change a Container’s layout manager to be a different
one by invoking setLayout().
Event Handling
-
All of the events dispatched by AWT’s components use event
classes that are subclasses of AWTEvent, which is in java.awt. These subclasses
are defined in the java.awt.event package.
-
The AWT does not notify your event handler of every event
that occurs over a component, as in the old days of 1.0.2. Now, AWT informs
your event handler only about the events it is interested in.
-
Define a class which implements the necessary Listeners and
then use the Component addABCListener() method to register an interest
in a certain type of event, e.g. addMouseListener(this).
-
The Listener interfaces inherit directly from java.util.EventListener.
-
The Listener interfaces are
-
ActionListener
-
AdjustmentListener
-
ComponentListener
-
FocusListener
-
ItemListener
-
KeyListener
-
MouseListener
-
MouseMotionListener
-
TextListener
-
WindowListener
-
If you define a class which implements a listener, you must
obviously include stubs for those listener methods not implemented as interfaces
are implicitly abstract and failure to implement all of the
methods would result in an abstract subclass.
-
The Listener methods are as follows: (Note - all are declared
as public void and all take only one parameter which is an
Event of the same name as the Listener, i.e. ActionListener methods take
an ActionEvent etc.
Listener |
Methods |
ActionListener |
actionPerformed |
AdjustmentListener |
adjustmentPerformed |
ComponentListener |
componentHidden
componentMoved
componentResized
componentShown |
ContainerListener |
componentAdded
componentRemoved |
FocusListener |
focusGained
focusLost |
ItemListener |
itemStateChanged |
KeyListener |
keyPressed
keyReleased
keyTyped |
MouseListener |
mouseClicked
mouseEntered
mouseExited
mousePressed
mouseReleased |
MouseMotionListener |
mouseDragged
mouseMoved |
TextListener |
textValueChanged |
WindowListener |
windowClosed
windowClosing
windowDeiconified
windowActivated
windowDeactivated
windowIconified
windowOpened |
See pages 360-363 for Event classes.
-
There’s an Adapter class to match each Listener interface.
Each Adapter class defines no-op stubs for the methods declared in the
corresponding interface. So can extend an Adapter rather than implement
a Listener interface (but this only makes sense when the object that will
listen for and handle the event has no other responsibilities).
Passing Arguments to Programs
-
The main() method must be declared as a public, static
method that does not return a value and takes an array of String objects.
The order of public and static, and the way in which the String array is
defined, is not strictly enforced.
-
When main() ends, that may or may not be the end of
the program. The JVM will run until the only remaining threads are daemon
threads. If main() does not spawn any more threads, then the program
will end when main() ends.
Embedding Applets into Web Pages
-
The applet tag requires three codewords - code,
width and height, e.g. <applet code=Metric.class width=200
height=100></applet>
-
If the applet is loaded relative to the page, there are two
things that can change the base location - one of which is if the HTML
file itself contains a <base> tag - this tag specifies where to look
for the applet class.
-
The conventional way to pass a parameter to an applet is
to use the <param> tag, using one <param> tag per parameter. Each
<param> tag can take only one parameter.
-
Each parameter value can be retrieved by the applet as a
String, using methods defined in class Applet.
-
If you want to pass a different type of value, such as an
int or a boolean, you must convert it from a String, most likely by using
a wrapper class.
-
If you’d like a parameter to contain spaces, you should place
this value between quotes. Otherwise it’s not strictly necessary to pass
params in quotes (good style though).
-
You retrieve the value of a parameter using the getParameter()
method defined by the Applet class. This method returns a String containing
the value of the parameter, or null if the parameter was notdefined
at all.
-
Class Applet inherits from Panel.
-
When an applet instance is first instantiated, Java invokes
the applet’s init() method.
-
When the Web page containing the applet is about to appear,
Java invokes the applet’s start() method.
-
When the Web page is about to be replaced with another page,
Java invokes the applets stop() method.
-
When the Web page is removed from the browser’s cache and
the applet instance is about to go away, Java invokes the applet’s destroy()
method.
Inner Classes
-
In Java 1.1 you can define classes inside classes - these
are known as "inner classes".
-
If you define an inner class at the same level as the enclosing
class’ instance variables, the inner class can access those instance variables
- no matter what their access control.
-
If you define an inner class within a method, the inner class
can access the enclosing class’ instance variables and also the local variables
and parameter for that method.
-
If you do reference local variables or parameters from an
inner class, those variables or parameters must be declared as final
to help guarantee data integrity.
-
You can also define an anonymous class - a class without
a name. See p.399 Exam Guide for syntax.
-
If you’d like to refer to the current instance of the enclosing
class, you can write EnclosingClassName.this.
-
If you need to refer to the inner class using a fully qualified
name, you can write EnclosingClassName.InnerClassName.
-
If your inner class is not defined as static you can
only create new instances of this class from a non-static method.
-
Anonymous classes cannot have const
JAR Files
-
JAR stands for "Java Archive". The 1.1 JDK comes with a utility
called ‘jar’ that creates JAR files. Example syntax: jar -cf Jungle.jar
Panther.class Leopard.class
-
Directories are processed recursively
-
Can specify a JAR file in a Web page by adding ‘archive="jars/Jungle.jar"
’ to the <applet> tag. E.g. <applet code=ExampleApplet.class archive="jars/example.jar"
width=200 height=110> </applet>
-
You can also define more than one JAR file in the archive
value by listing them all within the quotes and separating their names
with commas.
Serializing Objects
-
In Java 1.1 it is now possible to read and write objects
as well as primitive data types, using classes that implement ObjectInput
and ObjectOutput. These two interfaces extend DataInput and DataOutput
to read or write an object. ObjectInputStream and ObjectOutputStream implement
these interfaces.
-
If a class implements the Serializable interface, then its
public
and protected instance variables will be read from and written to
the stream automatically when you use ObjectInputStream and ObjectOutputStream.
-
If an instance variable refers to another object, it will
also be read or written, and this continues recursively.
-
If the referenced object does not implement the Serializable
interface, Java will throw a NotSerializableException.
-
The Serializable interface serves only to identify those
instances of a particular class that can be read from and written to a
stream. It does not actually define any methods that you must implement.
-
If you create your own class and want to keep certain data
from being read or written, you can declare that instance variable using
the transient keyword. Java skips any variable declared as transient
when it reads and writes the object following the Serializable protocol.
Reflection
-
Using the Reflection API, a program can determine a class’
accessible fields, methods and constructors at runtime.
More Java Questions
Java Books
Java Certification,
Programming, JavaBean and Object Oriented Reference Books
Return to : Java
Programming Hints and Tips
All the site contents are Copyright © www.erpgreat.com
and the content authors. All rights reserved.
All product names are trademarks of their respective
companies.
The site www.erpgreat.com is not affiliated with or endorsed
by any company listed at this site.
Every effort is made to ensure the content integrity.
Information used on this site is at your own risk.
The content on this site may not be reproduced
or redistributed without the express written permission of
www.erpgreat.com or the content authors.
|