You are on page 1of 46

cohesive adj.

cohesive force
havoc n.; ; ; ;
stifle vt. , (!") #$(up) [%&]'( stifle sobs
[yawn])*+,[-.]
stifle a rebellion !The smoke stifled the fireman./0123
45
Polymorphism n.67(89)
ellipsis .(pl. ses [si!"]):;<=>?:@<=>AB(
C
, ... ")
nuance n.(DEFGHFIJFKLFMN")OP; QORN, SJ; IH
wrath n.TU, VU WXYZ; [\;:]<S^, _\nurse one#s wrath `a
bcslow to wrath defgU
monolithic ad$. hi hjklthe monolithic buildin%s mnop
qrsrdtuvwxya sin%le monolithic party srdz{|}
~
ramification n.z, z; z, z; z; z? , {; z,
; ,
in a nutshell j
invocation n.[],A(),(??)x; (?F")
; gy
reiterate vt.[]; ;
sneak [sni!k]vi.y(-), , x,x,[&](")

sneak about a place b-y sneak past a %uard


sneak into a theatre
ro%ue n.
mas&uerade n.; [][]; ; ;
vi.; ; , strip off sb#s mas&uerades

obfuscate vt.; ,;
darn vt., 'is socks had been darned a%ain and a%ain.
r5
lucid ad$. f , (he does have occasional lucid
moments.r
shun vt.(shunned; shunnin%)[]("), , )aterialists
face truth, whereas idealists shun it., c
5
terse ad$.(, "); a terse and vi%orous style
a terse reply r
e*cruciatin% ad$.; ; ),, atin%ly
va%ary n.[]x; []; the ries of
women#s fashions
ries of the mind !"#
ternary ad$.w$%z&', $, $(,)$:<w$*d+,-.&'
; $,('z),:/<$,, $/, $0
+Fthe difference between abstract class and interface
an abstract class can define both abstract and nonabstract
methods, an interface can have only abstract methods
,ll interface methods are implicitly public and abstract. -n
other words,you do not need to actually type the public or
abstract modifiers in the method declaration, but the method is
still always public and abstract.
,ll variables defined in an interface must be public, static,
and final.in other words, interfaces can declare only constants,
not instance variables.
-nterface methods must not be static.
/ecause interface methods are abstract, they cannot be marked
final,strictfp, or native.
,n interface can extend one or more other interfaces.
,n interface cannot e*tend anythin% but another interface.
,n interface cannot implement another interface or class.
,n interface must be declared with the keyword interface.
-nterface types can be used polymorphically
both of these declarations are le%al, and functionally identical!
public abstract interface 0ollable 1 2
public interface 0ollable 1 2
Typin% in the public and abstract modifiers on the methods is
redundant, since all interface methods are implicitly public and
abstract
The followin% interface method declarations won#t compile!
final void bounce(); 33 final and abstract can never be used
33 to%ether, and abstract is implied
static void bounce(); 33 interfaces define instance methods
private void bounce(); 33 interface methods are always public
protected void bounce(); 33 (same as above)
4F, default member may be accessed only if the class accessin% the
member belon%s to the same packa%e, whereas a protected member
can be accessed (throu%h inheritance) by a subclass even if the
subclass is in a different package.
Default and protected behavior differ only when we talk about
subclasses.-f the protected keyword is used to define a member,
any subclass of the class declarin% the member can access it
through inheritance. -t doesn#t matter if the superclass and
subclass are in different packa%es, the protected superclass
member is still visible to the subclass (althou%h visible only in
a very specific way as we#ll see a little later). This is in
contrast to the default behavior, which doesn#t allow a subclass
to access a superclass member unless the subclass is in the same
packa%e as the superclass.
when you think protected, think package + kids. , class with a
protected member is markin% that member as havin% packa%elevel
access for all classes, but with a special e*ception for
subclasses outside the packa%e.
The bottom line! when a subclassoutsidethepacka%e inherits a
protected member, the member is essentially private inside the
subclass, such that only the subclass and its subclasses can
access it.
5Fthere is only one modifier that can ever be applied to local
variables.final.
6F7et#s look at some le%al and ille%al varar% declarations!
7e%al!
void do(tuff(int... *) 1 2 33 e*pects from 8 to many ints
33 as parameters
void do(tuff4(char c, int... *) 1 2 33 e*pects first a char,
33 then 8 to many ints
void do(tuff5(,nimal... animal) 1 2 33 8 to many ,nimals
-lle%al!
void do(tuff6(int *...) 1 2 33 bad synta*
void do(tuff9(int... *, char... y) 1 2 33 too many varar%s
void do(tuff:((trin%... s, byte b) 1 2 33 varar% must be last
9F;omparison of modifiers on variables vs. methods
local variables! final
nonlocal variables! final, public, protected, private, static,
transient, volatile
methods! final, public, protected, private, static, abstract,
synchroni"ed, strictfp, native
:F<eclarin% an enum outside a class!
enum ;offee(i"e 1 /-=, '>=?, @A?0B'?7)-C= 2 33 this cannot be
33 private or protected
class ;offee 1
;offee(i"e si"e;
2
public class ;offeeTest+ 1
public static void main((trin%[] ar%s) 1
;offee drink D new ;offee();
drink.si"e D ;offee(i"e./-=; 33 enum outside class
2
2
The followin% is C@T le%al!
public class ;offeeTest+ 1
public static void main((trin%[] ar%s) 1
enum ;offee(i"e 1 /-=, '>=?, @A?0B'?7)-C= 2 33 B0@C=E
;annot
33 declare enums in methods
;offee drink D new ;offee();
drink.si"e D ;offee(i"e./-=;
2
2
?ach of the enumerated ;offee(i"e types are actually instances of
;offee(i"e.
33 conceptual e*ample of how you can think
33 about enums
class ;offee(i"e 1
public static final ;offee(i"e /-= D
new ;offee(i"e(F/-=F, 8);
public static final ;offee(i"e '>=? D
new ;offee(i"e(F'>=?F, +);
public static final ;offee(i"e @A?0B'?7)-C= D
new ;offee(i"e(F@A?0B'?7)-C=F, 4);
public ;offee(i"e((trin% enumCame, int inde*) 1
33 stuff here
2
public static void main((trin%[] ar%s) 1
(ystem.out.println(;offee(i"e./-=);
2
2
GFThe overridin% method cannot have a more restrictive access
modifier than the method bein% overridden (for e*ample, you can#t
override a method marked public and make it protected).
The rules for overridin% a method are as follows!
1The ar%ument list must e*actly match that of the overridden
method. -f they don#t match, you can end up with an overloaded
method you didn#t intend.
1The return type must be the same as, or a subtype of, the return
type declared in the ori%inal overridden method in the
superclass.
1 The access level can#t be more restrictive than the overridden
method#s.
1 The access level ;,C be less restrictive than that of the
overridden method.
1-nstance methods can be overridden only if they are inherited by
the subclass., subclass within the same packa%e as the instance#s
superclass can override any superclass method that is not marked
private or final. , subclass in a different packa%e can override
only those nonfinal methods marked public or protected (since
protected methods are inherited by the subclass).
1 The overridin% method ;,C throw any unchecked (runtime)
e*ception, re%ardless of whether the overridden method declares
the e*ception.
1 The overridin% method must C@T throw checked e*ceptions that
are new or broader than those declared by the overridden method.
Hor e*ample, a method that declares a HileCotHound?*ception
cannot be overridden by a method that declares a (I7?*ception,
?*ception, or any other nonruntime e*ception unless it#s a
subclass of HileCotHound?*ception.
1The overridin% method can throw narrower or fewer e*ceptions.
Just because an overridden method Ftakes risksF doesn#t mean that
the overridin% subclass# e*ception takes the same risks. /ottom
line! an overridin% method doesn#t have to declare any e*ceptions
that it will never throw, re%ardless of what the overridden
method declares.
1 Kou cannot override a method marked final.
1 Kou cannot override a method marked static. Be#ll look at an
e*ample in a few pa%es when we discuss static methods in more
detail.
1-f a method can#t be inherited, you cannot override it. 0emember
that overridin% implies that you#re reimplementin% a method you
inheritedE Hor e*ample, the followin% code is not le%al, and even
if you added an eat() method to 'orse, it wouldn#t be an override
of ,nimal#s eat() method.
public class Test,nimals 1
public static void main ((trin% [] ar%s) 1
'orse h D new 'orse();
h.eat(); // Not legal because Horse didn't inherit
eat()
2
2
class ,nimal 1
private void eat() 1
(ystem.out.println(F=eneric ,nimal ?atin% =enericallyF);
2
2
class 'orse e*tends ,nimal 1 2
Using super to invoke an overridden method only applies to
instance methods. (Remember, static methods cant be overridden.!
If a method is overridden but you use a polymorphic (supertype)
reference to refer to the subtype object with the overriding
method, the compiler assumes youre calling the supertype version
of the method. If the supertype version declares a checked
exception, but the overriding subtype method does not, the
compiler still thinks you are calling a method that declares an
exception.
Lets take a look at an example
class ,nimal 1
public void eat() throws ?*ception 1
33 throws an ?*ception
2
2
class <o%4 e*tends ,nimal 1
public void eat() 1 33 no ?*ceptions 2
public static void main((trin% [] ar%s) 1
,nimal a D new <o%4();
<o%4 d D new <o%4();
d.eat(); 33 ok
a.eat(); // compiler error -
// unreported exception
2
2
!his code will not compile because of the "xception declared on
the #nimal eat() method. !his happens even though, at runtime,
the eat() method used would be the $og version, which does not
declare the exception.
Examples of Legal and Illegal Method !errides
7et#s take a look at overridin% the eat() method of ,nimal!
public class ,nimal 1
public void eat() 1 2
2
Table 4+ lists e*amples of ille%al overrides of the ,nimal eat()
method, %iven the precedin% version of the ,nimal class.
Illegal !erride "ode #roblem $ith
the "ode
private void eat() 1 2 ,ccess modifier is more
restrictive
public void eat() throws -@?*ception 1 2 <eclares a checked
e*ception not
defined by superclass version
public void eat((trin% food) 1 2 , le%al overload, not an
override, because
the ar%ument list chan%ed
public (trin% eat() 1 2 Cot an override because
of the return type,
not an overload either because thereLs no chan%e in
the ar%ument list
MF ,n interface can e*tend more than one interface
interface %ounceable extends Mo!eable& 'pherical ( // o)*
void bounce();
void set/ounceHactor(int bf);
2
interface )oveable 1
void move-t();
2
interface (pherical 1
void do(phericalThin%();
2
class Hoo 1 2 33 @N
class /ar implements Hoo 1 2 33 CoE ;an#t implement a class
interface /a" 1 2 33 @N
interface Hi 1 2 33 @N
interface Hee implements /a" 1 2
33 CoE -nterface can#t implement an interface
interface Oee implements Hoo 1 2
33 CoE -nterface can#t implement a class
interface Ooo e*tends Hoo 1 2
33 CoE -nterface can#t e*tend a class
interface /oo e*tends Hi 1 2
33 @N. -nterface can e*tend an interface
class Toon e*tends Hoo, /utton 1 2
33 CoE ;lass can#t e*tend multiple classes
class Ooom implements Hi, Hee 1 2
33 @N. class can implement multiple interfaces
interface Aroom e*tends Hi, Hee 1 2
33 @N. interface can e*tend multiple interfaces
class Kow e*tends Hoo implements Hi 1 2
33 @N. ;lass can do both (e*tends must be +st)
PFsi* rules for returnin% a value!
+. Kou can return null in a method with an ob$ect reference
return type.
public /utton do(tuff() 1
return null;
2
4. ,n array is a perfectly le%al return type.
public (trin%[] %o() 1
return new (trin%[] 1FHredF, F/arneyF, FBilmaF2;
2
5. -n a method with a primitive return type, you can return any
value or
variable that can be implicitly converted to the declared return
type.
public int foo() 1
char c D #c#;
return c; 33 char is compatible with int
2
6. -n a method with a primitive return type, you can return any
value or
variable that can be e*plicitly cast to the declared return type.
public int foo () 1
float f D 54.9f;
return (int) f;
2
9. Kou must not return anythin% from a method with a void return
type.
public void bar() 1
return Fthis is itF; 33 Cot le%alEE
2
:. -n a method with an ob$ect reference return type, you can
return any
ob$ect type that can be implicitly cast to the declared return
type.
public ,nimal %et,nimal() 1
return new 'orse(); 33 ,ssume 'orse e*tends ,nimal
2
public @b$ect %et@b$ect() 1
int[] nums D 1+,4,52;
return nums; 33 0eturn an int array,
33 which is still an ob$ect
2
public interface ;hewable 1 2
public class =um implements ;hewable 1 2
public class Test;hewable 1
33 )ethod with an interface return type
public ;hewable %et;hewable() 1
return new =um(); 33 0eturn interface implementer
2
2
+8F+ules for "onstructors
1;onstructors can use any access modifier, includin% private. (,
privateconstructor means only code within the class itself can
instantiate an ob$ectof that type, so if the private constructor
class wants to allow an instanceof the class to be used, the
class must provide a static method or variable thatallows access
to an instance created from within the class.)
1The constructor name must match the name of the class.
1;onstructors must not have a return type.
1-t#s le%al (but stupid) to have a method with the same name as
the class,but that doesn#t make it a constructor. -f you see a
return type, it#s a methodrather than a constructor. -n fact, you
could have both a method and aconstructor with the same name.the
name of the class.in the same class,and that#s not a problem for
Java. /e careful not to mistake a method for aconstructor.be sure
to look for a return type.
1-f you don#t type a constructor into your class code, a default
constructor willbe automatically %enerated by the compiler.
1The default constructor is ,7B,K( a noar% constructor.
1-f you want a noar% constructor and you#ve typed any other
constructor(s)into your class code, the compiler won#t provide
the noar% constructor (orany other constructor) for you. -n
other words, if you#ve typed in a constructorwith ar%uments, you
won#t have a noar% constructor unless you type it inyourself E
1?very constructor has, as its first statement, either a call to
an overloadedconstructor (this()) or a call to the superclass
constructor (super()), althou%hremember that this call can be
inserted by the compiler.
1-f you do type in a constructor (as opposed to relyin% on the
compiler%enerateddefault constructor), and you do not type in
the call to super() or a callto this(), the compiler will insert
a noar% call to super() for you, as the veryfirst statement in
the constructor.
1, call to super() can be either a noar% call or can include
ar%uments passedto the super constructor.
1, noar% constructor is not necessarily the default (i.e.,
compilersupplied)constructor, althou%h the default constructor
is always a noar% constructor.The default constructor is the one
the compiler providesE Bhile the defaultconstructor is always a
noar% constructor, you#re free to put in your own
noar%constructor.
1Kou cannot make a call to an instance method, or access an
instance variable,until after the super constructor runs.
1@nly static variables and methods can be accessed as part of the
call to super()or this(). (?*ample! super(,nimal.C,)?) is @N,
because C,)? isdeclared as a static variable.)
1,bstract classes have constructors, and those constructors are
always calledwhen a concrete subclass is instantiated.
1-nterfaces do not have constructors. -nterfaces are not part of
an ob$ect#sinheritance tree.
1The only way a constructor can be invoked is from within another
constructor.-n other words, you can#t write code that actually
calls a constructor asfollows!
class 'orse 1
'orse() 1 2 33 constructor
void do(tuff() 1
'orse(); 33 callin% the constructor ille%alE
2
2
,e- +ule. /he first line in a constructor must be a call to
super() or a call to this()0
Co e*ceptions. -f you have neither of those calls in your
constructor, the compiler will insert the noar% call to super().
-n other words, if constructor ,() has a call to this(), the
compiler knows that constructor ,() will not be the one to invoke
super().
The precedin% rule means a constructor can never have both a call
to super() and a call to this(). /ecause each of those calls must
be the first statement in a constructor, you can#t le%ally use
both in the same constructor. That also means the compiler will
not put a call to super() in any constructor that has a call to
this().
++Fremember that static methods cant be overriddenE This doesn#t
mean they can#t be redefined in a subclass, but redefinin% and
overridin% aren#t the same thin%. 7et#s take a look at an e*ample
of a redefined (remember, not overridden), static method!
class ,nimal 1
static void do(tuff() 1
(ystem.out.print(Fa F);
2
2
class <o% e*tends ,nimal 1
static void dostuff() 1 33 it#s a redefinition,
33 not an override
(ystem.out.print(Fd F);
2
public static void main((trin% [] ar%s) 1
,nimal [] a D 1new ,nimal(), new <o%(), new ,nimal()2;
for(int * D 8; * Q a.len%th; *RR)
a1x20do'tuff()3 // in!o)e the static method
2
2
0unnin% this code produces the output!
a a a
0emember, the synta* a[*].do(tuff() is $ust a shortcut (the
synta* trick)Sthe compiler is %oin% to substitute somethin% like
,nimal.do(tuff() instead.
+4Fchar a D 8*MP4; 33 he*adecimal literal
char b D PM4; 33 int literal
char c D (char)G8888; 33 The cast is re&uired; G8888 is out of
char ran%e
char d D (char) PM; 33 0idiculous, but le%al
,nd the followin% are not le%al and produce compiler errors!
char e D 4P; 33 Possible loss of precision; needs a cast
char f D G8888 33 Possible loss of precision; needs a cast
byte b D 5; 33 Co problem, 5 fits in a byte
byte c D M; 33 Co problem, M fits in a byte
byte d D b R c; 33 (hould be no problem, sum of the two bytes
fits in a byte
The last line won#t compileE Kou#ll %et an error somethin% like
this!
Test/ytes.$ava!9! possible loss of precision
found ! int
re&uired! byte
byte c D a R b;
-t would
have compiled if we#d done the explicit cast!
byte c D (byte) (a R b);
float a D +88.88+f;
int b D (int)a; 33 ?*plicit cast, the float could lose info
Bhen you narrow a primitive, Java simply truncates the hi%her
order bits that won#t fit. -n other words, it loses all the bits
to the left of the bits you#re narrowin% to.
byte b D 5;
b D (byte) (b R G); 33 Bon#t compile without the
33 cast, since b R G results in an int
arrays must always be %iven a si"e at the time they are
constructed.The JA) needs the si"e to allocate the appropriate
space on the heap for the newarray ob$ect. -t is never le%al, for
e*ample, to do the followin%!
int[] car7ist D new int[]; 33 Bill not compile; needs a si"e
(o don#t do it, and if you see it on the test, run screamin%
toward the nearest answer marked F;ompilation fails.F
, twodimensional array (an array of arrays) can be initiali"ed
as follows!
int[][] scores D new int[5][];
33 <eclare and create an array holdin% three references
33 to int arrays
scores[8] D new int[6];
33 the first element in the scores array is an int array
33 of four int elements
scores[+] D new int[:];
33 the second element in the scores array is an int array
33 of si* int elements
scores[4] D new int[+];
33 the third element in the scores array is an int array
33 of one int element
+5F, static initiali"ation block runs once, when the class is
first loaded.-nstance init block code runs ri%ht after the call
to super() in a constructor, in other words, after all super
constructors have run.
+6F-n order to save memory, two instances of the followin% wrapper
ob$ects will always be DD when their primitive values are the
same!
/oolean
/yte
;haracter from Tu8888 to Tu88Gf (Gf is +4G in decimal)
(hort and -nte%er from +4M to +4G
-nte%er i+ D +888;
-nte%er i4 D +888;
if(i+ ED i4) (ystem.out.println(Fi+ and i4different ob$ectsF);
if(i+.e&uals(i4)) (ystem.out.println(Fmeanin%fully e&ualF);
the result! (i+,i4U+4G)
i+ and i4different ob$ects
meanin%fully e&ual
-nte%er i5 D +8;
-nte%er i6 D +8;
if(i5 DD i6) (ystem.out.println(Fi5 and i6 are same ob$ectF);
if(i5.e&uals(i6)) (ystem.out.println(Fmeanin%fully e&ualF);
the result! (i5,i6 Q+4G)
i5 and i6 are same ob$ect
meanin%fully e&ual
+9Fclass ,dd/o*in% 1
static !oid %o(-nte%er *) 1 (ystem.out.println(F-nte%erF); 2
static !oid %o(long *) 1 (ystem.out.println(Flon%F); 2
public static !oid main((trin% [] ar%s) 1
int i D 9;
go(i); 33 which %o() will be invokedV
2
2
lon%
if the only version of the %o() method was one that took
an -nte%er, then Java 9#s bo*in% capability would allow the
invocation of %o() to
succeed. 7ikewise, if only the lon% version e*isted, the compiler
would use it to
handle the %o() invocation. The &uestion is, %iven that both
methods e*ist, which
one will be usedV -n other words, does the compiler think that
widenin% a primitive
parameter is more desirable than performin% an autobo*in%
operationV The answer is
that the compiler will choose widenin% over bo*in%, so the output
will be lon%
Java 9#s desi%ners decided that the most important rule should be
that pree*istin%
code should function the way it used to, so since widenin%
capability already e*isted,
a method that is invoked via widenin% shouldn#t lose out to a
newly created method
that relies on bo*in%. /ased on that rule, try to predict the
output of the followin%!
class ,ddAarar%s 1
static void %o(int *, int y) 1 (ystem.out.println(Fint,intF);2
static void %o(byte... *) 1 (ystem.out.println(Fbyte... F); 2
public static void main((trin%[] ar%s) 1
byte b D 9;
%o(b,b); 33 which %o() will be invokedV
2
2
,s you probably %uessed, the output is
int,int
/ecause, once a%ain, even thou%h each invocation will re&uire
some sort of
conversion, the compiler will choose the older style before it
chooses the newer
style, keepin% e*istin% code more robust. (o far we#ve seen that
. Bidenin% beats bo*in%
.Bidenin% beats varar%s
,t this point, in&uirin% minds want to know, does bo*in% beat
varar%sV
class /o*@rAarar% 1
static void %o(/yte *, /yte y)
1 (ystem.out.println(F/yte, /yteF); 2
static void %o(byte... *) 1 (ystem.out.println(Fbyte... F); 2
public static void main((trin% [] ar%s) 1
byte b D 9;
%o(b,b); 33 which %o() will be invokedV
2
2
,s it turns out, the output is
/yte, /yte
+:FIts tempting to think that you might be able to widen an
Integer wrapper to a Long wrapper, but the following will %&!
compile
class <o%6 1
public static void main((trin% [] ar%s) 1
<o%6 d D new <o%6();
d.test(new -nte%er(9)); 33 can#t widen an -nte%er
33 to a 7on%
2
void test(7on% *) 1 2
2
'emember, none of the wrapper classes will widen from one to
another( )ytes wont widen to *horts, *horts wont widen to Longs,
etc.
!erloading 4hen "ombining 4idening and %oxing
Be#ve looked at the rules that apply when the compiler can match
an invocation to
a method by performin% a sin%le conversion. Cow let#s take a look
at what happens
when more than one conversion is re&uired. -n this case the
compiler will have to
widen and then autobo* the parameter for a match to be made!
class Biden,nd/o* 1
static void %o(7on% *) 1 (ystem.out.println(F7on%F); 2
public static void main((trin% [] ar%s) 1
byte b D 9;
%o(b); 33 must widen then bo* ille%al
2
2
This is $ust too much for the compiler!
Biden,nd/o*.$ava!:! %o($ava.lan%.7on%) in Biden,nd/o* cannot be
applied to (byte)
(tran%ely enou%h, it -( possible for the compiler to perform a
bo*in% operation
followed by a widenin% operation in order to match an invocation
to a method. This
one mi%ht blow your mind!
class /o*,ndBiden 1
static void %o(@b$ect o) 1
/yte b4 D (/yte) o; 33 ok it#s a /yte ob$ect
(ystem.out.println(b4);
2
public static void main((trin% [] ar%s) 1
byte b D 9;
%o(b); 33 can this byte turn into an @b$ect V
2
2
This compiles (E), and produces the output!
9
BowE 'ere#s what happened under the covers when the compiler,
then the JA),
%ot to the line that invokes the %o() method!
+. The byte b was bo*ed to a /yte.
4. The /yte reference was widened to an @b$ect (since /yte
e*tends @b$ect).
5. The %o() method %ot an @b$ect reference that actually refers
to a /yte
ob$ect.
6. The %o() method cast the @b$ect reference back to a /yte
reference (remember, there was never an ob$ect of type @b$ect in
this scenario, only an ob$ect
of type /yteE).
9. The %o() method printed the /yte#s value.
Bhy didn#t the compiler try to use the bo*thenwiden lo%ic when
it tried to deal with the Biden,nd/o* classV Think about itSif it
tried to bo* first, the byte would have been converted to a /yte.
Cow we#re back to tryin% to widen a /yte to a 7on%, and of
course, the -(, test fails.
class Aarar% 1
static void wideWvarar%(lon%... *)
1 (ystem.out.println(Flon%...F); 2
static void bo*Wvarar%(-nte%er... *)
1 (ystem.out.println(F-nte%er...F); 2
public static void main((trin% [] ar%s) 1
int i D 9;
wideWvarar%(9,9); 33 needs to widen and use varar%s
bo*Wvarar%(9,9); 33 needs to bo* and use varar%s
2
2
This compiles and produces!
lon%...
-nte%er...
'ere#s a review of the rules for overloadin% methods usin%
widenin%, bo*in%, and varar%s!
. Primitive widenin% uses the FsmallestF method ar%ument
possible.
.>sed individually, bo*in% and varar%s are compatible with
overloadin%.
.Kou ;,CC@T widen from one wrapper type to another. (-(, fails.)
.Kou ;,CC@T widen and then bo*. (,n int can#t become a 7on%.)
.Kou can bo* and then widen. (,n int can become an @b$ect, via
-nte%er.)
.Kou can combine varar%s with either widenin% or bo*in%.
+GF/ric)- Little finali5e() 6otcha's
There are a couple of concepts concernin% finali"e() that you
need to remember.
. Hor any %iven ob$ect, finali"e() will be called only once (at
most) by the%arba%e collector.
. ;allin% finali"e() can actually result in savin% an ob$ect from
deletion.
7et#s look into these statements a little further. Hirst of all,
remember that any code that you can put into a normal method you
can put into finali"e(). Hor e*ample, in the finali"e() method
you could write code that passes a reference to the ob$ect in
&uestion back to another ob$ect, effectively uneligibli"ing the
ob$ect for %arba%e collection. -f at some point later on this
same ob$ect becomes eli%ible for %arba%e collection a%ain, the
%arba%e collector can still process this ob$ect and delete it.
The %arba%e collector, however, will remember that,
+MF=iven!
class ;ard/oard 1
(hort story D 9;
;ard/oard %o(;ard/oard cb) 1
cb D null;
return cb;
2
public static void main((trin%[] ar%s) 1
;ard/oard c+ D new ;ard/oard();
;ard/oard c4 D new ;ard/oard();
;ard/oard c5 D c+.%o(c4);
c+ D null;
33 do (tuff
2
2
Bhen 33 do(tuff is reached, how many ob$ects are eli%ible for =;V
,. 8
/. +
;. 4
<. ;ompilation fails.
?. -t is not possible to know.
H. ,n e*ception is thrown at runtime.
7ns$er.
X " is correct. @nly one ;ard/oard ob$ect (c+) is eli%ible, but
it has an associated (hort
wrapper ob$ect that is also eli%ible.
X 7& %& 8& E& and 9 are incorrect based on the above. (@b$ective
G.6)
+PF=iven!
class ,lien 1
(trin% invade(short ships) 1 return Fa fewF; 2
(trin% invade(short... ships) 1 return FmanyF; 2
2
class <efender 1
public static void main((trin% [] ar%s) 1
(ystem.out.println(new ,lien().invade(G));
2
2
Bhat is the resultV
,. many
/. a few
;. ;ompilation fails.
<. The output is not predictable.
?. ,n e*ception is thrown at runtime.
7ns$er.
X " is correct, compilation fails. The varar%s declaration is
fine, but invade takes a short,
so the ar%ument G needs to be cast to a short. Bith the cast, the
answer is %, #a few#.
X 7& %& 8& and E are incorrect based on the above. (@b$ective
+.5)
48F=iven!
+. class <ims 1
4. public static void main((trin%[] ar%s) 1
5. int[][] a D 11+,4,2, 15,622;
6. int[] b D (int[]) a[+];
9. @b$ect o+ D a;
:. int[][] a4 D (int[][]) o+;
G. int[] b4 D (int[]) o+;
M. (ystem.out.println(b[+]);
P. 2
+8. 2
Bhat is the resultV
,. 4
/. 6
;. ,n e*ception is thrown at runtime
<. ;ompilation fails due to an error on line 6.
?. ;ompilation fails due to an error on line 9.
H. ;ompilation fails due to an error on line :.
=. ;ompilation fails due to an error on line G.
7ns$er.
X " is correct. , ;lass;ast?*ception is thrown at line G because
o+ refers to an int[][]
not an int[]. -f line G was removed, the output would be 6.
X 7& %& 8& E& 9& and 6 are incorrect based on the above.
(@b$ective +.5)
4+F=iven!
class ?%%s 1
int doY(7on% *, 7on% y) 1 return +; 2
int doY(lon%... *) 1 return 4; 2
int doY(-nte%er *, -nte%er y) 1 return 5; 2
int doY(Cumber n, Cumber m) 1 return 6; 2
public static void main((trin%[] ar%s) 1
new ?%%s().%o();
2
void %o() 1
short s D G;
(ystem.out.print(doY(s,s) R F F);
(ystem.out.println(doY(G,G));
2
2
Bhat is the resultV
,. + +
/. 4 +
;. 5 +
<. 6 +
?. 4 5
H. 5 5
=. 6 5
7ns$er.
X 6 is correct. Two rules apply to the first invocation of doY().
Kou canLt widen and then bo*
in one step, and varar%s are always chosen last. Therefore you
canLt widen shorts to either
ints or lon%s, and then bo* them to -nte%ers or 7on%s. /ut you
can bo* shorts to (horts and
then widen them to Cumbers, and this takes priority over usin% a
varar%s method. The
second invocation uses a simple bo* from int to -nte%er.
X 7& %& "& 8& E& and 9 are incorrect based on the above.
(@b$ective 5.+)
44F=iven!
+. class ;onvert 1
4. public static void main((trin%[] ar%s) 1
5. 7on% *7 D new 7on%(69:7);
6. lon% *+ D 7on%.value@f(F+45F);
9. 7on% *4 D 7on%.value@f(F+45F);
:. lon% *5 D *7.lon%Aalue();
G. 7on% *6 D *7.lon%Aalue();
M. 7on% *9 D 7on%.parse7on%(F69:F);
P. lon% *: D 7on%.parse7on%(F+45F);
+8. 2
++. 2
Bhich will compile usin% Java 9, but will C@T compile usin% Java
+.6V (;hoose all that apply.)
,. 7ine 6.
/. 7ine 9.
;. 7ine :.
<. 7ine G.
?. 7ine M.
H. 7ine P.
7ns$er.
X 7& 8& and E are correct. /ecause of the methodsL return types,
these method calls re&uired
autobo*in% to compile.
X %& "& and 9 are incorrect based on the above. (@b$ective 5.+)
45F=iven!
+. class ?co 1
4. public static void main((trin%[] ar%s) 1
5. ?co e+ D new ?co();
6. ?co e4 D new ?co();
9. ?co e5 D new ?co();
:. e5.e D e4;
G. e+.e D e5;
M. e4 D null;
P. e5 D null;
+8. e4.e D e+;
++. e+ D null;
+4. 2
+5. ?co e;
+6. 2
,t what point is only a sin%le ob$ect eli%ible for =;V
,. ,fter line M runs.
/. ,fter line P runs.
;. ,fter line +8 runs.
<. ,fter line ++ runs.
?. ;ompilation fails.
H. Cever in this pro%ram.
=. ,n e*ception is thrown at runtime.
7ns$er.
X 6 is correct. ,n error at line +8 causes a
CullPointer?*ception to be thrown because
e4 was set to null in line M. -f line +8 was moved between lines
G and M, then 9 would be
correct, because until the last reference is nulled none of the
ob$ects is eli%ible, and once
the last reference is nulled, all three are eli%ible.
X 7& %& "& 8& E& and 9 are incorrect based on the above.
(@b$ective G.6)
46F=iven!
class /ird 1
1 (ystem.out.print(Fb+ F); 2
public /ird() 1 (ystem.out.print(Fb4 F); 2
2
class 0aptor e*tends /ird 1
static 1 (ystem.out.print(Fr+ F); 2
public 0aptor() 1 (ystem.out.print(Fr4 F); 2
1 (ystem.out.print(Fr5 F); 2
static 1 (ystem.out.print(Fr6 F); 2
2
class 'awk e*tends 0aptor 1
public static void main((trin%[] ar%s) 1
(ystem.out.print(Fpre F);
new 'awk();
(ystem.out.println(Fhawk F);
2
2
Bhat is the resultV
,. pre b+ b4 r5 r4 hawk
/. pre b4 b+ r4 r5 hawk
;. pre b4 b+ r4 r5 hawk r+ r6
<. r+ r6 pre b+ b4 r5 r4 hawk
?. r+ r6 pre b4 b+ r4 r5 hawk
H. pre r+ r6 b+ b4 r5 r4 hawk
=. pre r+ r6 b4 b+ r4 r5 hawk
'. The order of output cannot be predicted.
-. ;ompilation fails.
7ns$er.
X 8 is correct. (tatic init blocks are e*ecuted at class loadin%
time, instance init blocks run
ri%ht after the call to super() in a constructor. Bhen multiple
init blocks of a sin%le type
occur in a class, they run in order, from the top down.
X 7& %& "& E& 9& 6& H& and I are incorrect based on the above.
Cote! youLll probably never
see this many choices on the real e*amE(@b$ective +.5)
49F=iven!
class 'e*y 1
public static void main((trin%[] ar%s) 1
-nte%er i D 64;
(trin% s D (iQ68)VFlifeF!(iU98)VFuniverseF!Feverythin%F;
(ystem.out.println(s);
2
2
Bhat is the resultV
,. null
/. life
;. universe
<. everythin%
?. ;ompilation fails.
H. ,n e*ception is thrown at runtime.
,nswer!
X 8 is correct. This is a ternary nested in a ternary with a
little unbo*in% thrown in./oth of the ternary e*pressions are
false.
X 7& %& "& E& and 9 are incorrect based on the above.(@b$ective
G.:)
4:F=iven!
class Titanic 1
public static void main((trin%[] ar%s) 1
/oolean b+ D true;
boolean b4 D false;
boolean b5 D true;
if((b+ Z b4) [ (b4 Z b5) Z b5)
(ystem.out.print(Falpha F);
if((b+ D false) [ (b+ Z b5) [ (b+ [ b4))
(ystem.out.print(Fbeta F);
2
2
Bhat is the resultV
,. beta
/. alpha
;. alpha beta
<. ;ompilation fails.
?. Co output is produced.
H. ,n e*ception is thrown at runtime.
,nswer!
X E is correct. -n the second if test, the leftmost e*pression
is an assi%nment, not a comparison. @nce b+ has been set to
false, the remainin% tests are all false.
X 7& %& "& 8& and 9 are incorrect based on the above.(@b$ective
G.: )
4GF=iven!
class Heline 1
public static void main((trin%[] ar%s) 1
7on% * D 647;
7on% y D 667;
(ystem.out.print(F F R G R 4 R F F);
(ystem.out.print(foo() R * R 9 R F F);
(ystem.out.println(* R y R foo());33(34*5yx6,b5foo
678)
2
static (trin% foo() 1 return FfooF; 2
2Bhat is the resultV
,. P foo6G M:foo
/. P foo6G 6466foo
;. P foo649 M:foo
<. P foo649 6466foo
?. G4 foo6G M:foo
H. G4 foo6G 6466foo
=. G4 foo649 M:foo
'. G4 foo649 6466foo
-. ;ompilation fails.
,nswer!
X 6 is correct. ;oncatenation runs from left to ri%ht, and if
either operand is a (trin%,the operands are concatenated. -f both
operands are numbers they are added to%ether.>nbo*in% works in
con$unction with concatenation.
X 7& %& "& 8& E& 9& H& and I are incorrect based on the above.
(@b$ective G.:)
4MF, switch#s e*pression must evaluate to a char, byte, short,
int, or, as of Java 9, an enum. That means if you#re not usin% an
enum, only variables and values that can be automatically
promoted (in other words, implicitly cast) to an int are
acceptable. Kou won#t be able to compile if you use anythin%
else, includin% the remainin% numeric types of lon%, float, and
double.
, case constant must evaluate to the same type as the switch
e*pression can use, with one additional.and bi%.constraint! the
case constant must be a compile time constantE (ince the case
ar%ument has to be resolved at compile time, that means you can
use only a constant or final variable that is assi%ned a literal
value. -t is not enou%h to be final, it must be a compile time
constant. Hor e*ample!
final int a D +;
final int b;
b D 4;
int * D 8;
switch (*) 1
case a! 33 ok
case b! 33 compiler error
7ook at the followin% switch!
byte % D 4;
switch(%) 1
case 45!
case +4M!
2
This code won#t compile. ,lthou%h the switch ar%ument is le%al.a
byte is
implicitly cast to an int.the second case ar%ument (+4M) is too
lar%e for a byte,
and the compiler knows itE ,ttemptin% to compile the precedin%
e*ample %ives
you an error somethin% like
Test.$ava!:! possible loss of precision
found ! int
re&uired! byte
case +4M!
-t is le%al to levera%e the power of bo*in% in a switch
e*pression. Hor instance,
the followin% is le%al!
switch(new -nte%er(6)) 1
case 6! (ystem.out.println(Fbo*in% is @NF);
2
4PF
for(declaration : expression)
The two pieces of the
for
statement are
declaration The newly declared block variable, of a type compatible with the
elements of the array you are accessing. This variable will be available within
the
for
block, and its value will be the same as the current array element.
expression This must evaluate to the array you want to loop through. This
could be an array variable or a method call that returns an array. The array
can be any type: primitives, objects, even arrays of arrays. Using the above
defnitions, let's look at some legal and illegal enhanced
for
declarations:
int x;
long x2;
Long [] La = {4L, 5L, 6L};
long [] la = {7L, 8L, 9L};
int [][] twoDee = {{1,2,3}, {4,5,6}, {7,8,9}};
String [] sNums = {"one", "two", "three"};
Animal [] animals = {new Dog(), new Cat()};
// legal 'for' declarations
for(long y : la ) ; // loop thru an array of longs
for(long lp : La) ; // autoboxing the Long objects into longs
for(int[] n : twoDee) ; // loop thru the array of arrays
for(int n2 : twoDee[2]) ; // loop thru the 3rd sub-array
for(String s : sNums) ; // loop thru the array of Strings
for(Object o : sNums) ; // set an Object reference to each String
for(Animal a : animals) ; // set an Animal reference to each element
// ILLEGAL 'for' declarations
for(x2 : la) ; // x2 is already declared
for(int x2 : twoDee) ; // can't stuff an array into an int
for(int x3 : la) ; // can't stuff a long into an int
for(Dog d : animals) ; // you might get a Cat!
58FIt is illegal to use a
try
clause without either a
catch
clause or a
finally
clause. A
try
clause by itself will result in a compiler error.
Any
catch
clauses must immediately follow the
try
block. Any
finally
clause must immediately follow the last
catch
clause (or it must
immediately follow the
try
block if there is no
catch
). It is legal to
omit either the
catch
clause or the
finally
clause, but not both. You
cant sneak any code in between the
try
,
catch
, or
finally
blocks. The
following wont compile
try {
// do stuff
}
System.out.print("below the try"); //Illegal!
catch(Exception ex) { }
all non
RuntimeException
s are considered !checked! e"ceptions, because the
compiler checks to be certain you've acknowledged that !bad things could
happen here.!
Each method must either handle all checked exceptions by supplying a
catch
clause or list each unhandled checked exception as a thrown exception.
RuntimeException
,
Error
, and all of their subtypes are unchecked e"ceptions
and unchecked e"ceptions do not have to be specifed or handled.
5+F9:;<=>
:?@ABCEF;FG:AGHI
JKFLLMFLC<BN
OCB:=PQAR:K<OCSTTUVCWBAXLR:K<YACRAS=QZ[J<@C:A=NB<CSB=\F\I]
]
JKFLLOKF;<<[C<=QLMFLC<BN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
OCB:=PLa=SKKI
CBbNLa=<XOKF;<UVGQAR:K<OCSTTUVI
]JFCJWUZ[J<@C:A=[VN
La\^\I]
ObLC<?GASCG@B:=CK=ULVI
]
cc :=L<BCJAQ<W<B<
]
#hich, inserted independently at
// insert code here
, will compile, and
produce the output
b
$ %&hoose all that apply.'
(.
String doFileStuff() { return "b"; }
).
String doFileStuff() throws IOException { return "b"; }
&.
String doFileStuff(int x) throws IOException { return "b"; }
*.
String doFileStuff() throws FileNotFoundException { return "b"; }
+.
String doFileStuff() throws NumberFormatException { return "b"; }
,.
String doFileStuff() throws NumberFormatException,
FileNotFoundException { return "b"; }
(nswer:
A , D, E, and F are correct. -t.s okay for an overriding method to throw the
same e"ceptions, narrower e"ceptions, or no e"ceptions. (nd it.s okay for the
overriding method to throw any runtime e"ceptions.
B is incorrect, because the overriding method is trying to throw a broader
e"ception.C is incorrect. This method doesn.t override, so the output is
a
.
%/bjective 0.1'
54F2iven:
1. class Loopy {
2. public static void main(String[] args) {
3. int[] x = {7,6,5,4,3,2,1};
4. // insert code here
5. System.out.print(y + " ");
6. }
7. } }
#hich, inserted independently at line 1, compiles$ %&hoose all that apply.'
(.
for(int y : x) {
).
for(x : int y) {
&.
int y = 0; for(y : x) {
*.
for(int y=0, z=0; z<x.length; z++) { y = x[z];
+.
for(int y=0, int z=0; z<x.length; z++) { y = x[z];
,.
int y = 0; for(int z=0; z<x.length; z++) { y = x[z];
(nswer:
A , D, and F are correct. A is an e"ample of the enhanced
for
loop. D and
F are e"amples of the basic
for
loop.
B is incorrect because its operands are swapped. C is incorrect because the
enhanced
for
must declare its frst operand. E is incorrect synta" to declare
two variables in a
for
statement. %/bjective 0.0'
55F2iven:
1. class Ring {
2. final static int x2 = 7;
3. final static Integer x4 = 8;
4. public static void main(String[] args) {
5. Integer x1 = 5;
6. String s = "a";
7. if(x1 < 9) s += "b";
8. switch(x1) {
9. case 5: s += "c";
10. case x2: s += "d";
11. case x4: s += "e";
12. }
13. System.out.println(s);
14. }
15. }
#hat is the result$
(.
abc
).
abcde
&. &ompilation fails due only to an error on line 3.
*. &ompilation fails due only to an error on line 4.
+. &ompilation fails due only to an error on line 56.
,. &ompilation fails due only to an error on line 55.
2. &ompilation fails due to errors on multiple lines.
(nswer:
F is correct. (
switch
statement re7uires its
case
e"pressions to be
constants, and wrapper variables %even
final static
ones' aren.t considered
constants. The rest of the code is correct.
A, B, C, D, E, and G are incorrect based on the above. %/bjective 0.5'
56FStringBufer vs. StringBuilder
The 8tring)uilder class was added in 9ava :. -t has e"actly the same (;- as the
8tring)u<er class, e"cept 8tring)uilder is not thread safe. -n other words, its
methods are not synchroni=ed. %>ore about thread safety in &hapter ?.' 8un
recommends that you use 8tring)uilder instead of 8tring)u<er whenever
possible because 8tring)uilder will run faster %and perhaps jump higher'. 8o
apart from synchroni=ation, anything we say about 8tring)uilder's methods
holds true for 8tring)u<er's methods, and vice versa. @ou might encounter
7uestions on the e"am that have to do with using these two classes in the
creation of threadsafe applications,and we'll discuss how that works in
&hapter ?.
59F#hen you frst try to use the
Calendar
class you might notice that it's an
abstract class. @ou can't say
Calendar c = new Calendar(); // illegal, Calendar is abstract
-n order to create a
Calendar
instance, you have to use one of the overloaded
getInstance()
static factory methods:
Calendar cal = Calendar.getInstance();
The other &alendar method you should know for the e"am is the
roll()
method. The
roll()
method acts like the
add()
method, e"cept that when a
part of a *ate gets incremented or decremented, larger parts of the *ate will
not get incremented or decremented.
DateFormat
is another abstract class, so we can't use
new
to create instances of
DateFormat
. -n this case we used two factory methods,
getInstance()
and
getDateInstance()
. Aotice that
getDateInstance()
is overloadedB when we
discuss locales, we'll look at the other version of
getDateInstance()
that you'll
need to understand for the e"am.
!emember that both "ate#ormat and $umber#ormat ob%ects can
ha&e their locales set only at the time of instantiation. 'atch for
code that attempts to change the locale of an e(isting instance) no
such methods e(ist*
5:F
printf("format string", argument(s));
%[arg_index$][flags][width][.precision]conversion char
arg_index (n integer followed directly by a
$
, this indicates which argument
should be printed in this position.
fags #hile many Cags are available, for the e"am you'll need to know:
!
-
! Deft justify this argument
!E! -nclude a sign %E or
-
' with this argument
!6! ;ad this argument with =eroes
!,! Use localespecifc grouping separators %i.e., the comma in 50F,1:G'
!%! +nclose negative numbers in parentheses
widt This value indicates the minimum number of characters to print. %-f you
want nice even columns, you'll use this value e"tensively.'
precision ,or the e"am you'll only need this when formatting a Coatingpoint
number, and in the case of Coating point numbers, precision indicates the
number of
digits to print after the decimal point.
conversion The type of argument you'll be formatting. @ou'll need to know:
b
boolean c
char
d
integer f
Coating point s
string
Det's see some of these formatting strings in action:
int i1 = -123; int i2 = 12345;
System.out.printf(">%1$(7d< \n", i1);
System.out.printf(">%0,7d< \n", i2);
System.out.format(">%+-7d< \n", i2);
System.out.printf(">%2$b + %1$5d< \n", i1, false);
This produces:
> (123)<
>012,345<
>+12345 <
>false + -123<
5GF2iven:
bw
is a reference to a valid
BufferedWriter
(nd the snippet:
15. BufferedWriter b1 = new BufferedWriter(new File("f"));
16. BufferedWriter b2 = new BufferedWriter(new FileWriter("f1"));
17. BufferedWriter b3 = new BufferedWriter(new PrintWriter("f2"));
18. BufferedWriter b4 = new BufferedWriter(new BufferedWriter(bw));
#hat is the result$
(. &ompilation succeeds.
). &ompilation fails due only to an error on line 5:.
&. &ompilation fails due only to an error on line 5G.
*. &ompilation fails due only to an error on line 53.
+. &ompilation fails due only to an error on line 54.
,. &ompilation fails due to errors on multiple lines.
(nswer:
B is correct.
BufferedWriter
s can be constructed only by wrapping a #riter.
Dines 5G, 53,
and 54 are correct because
BufferedWriter
,
FileWriter
, and
PrintWriter
all
e"tend
#riter. %Aote:
BufferedWriter
is a decorator class. *ecorator classes are used
e"tensively
in the java.io package to allow you to e"tend the functionality of other
classes.'
A, C, D, E, and F are incorrect based on the above. %/bjective F.0'
5MF2iven:
JKFLLdefN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
OCB:=PLa\g\I
h=C<P<B[aijiI
KA=PkijiaijikI
:TU[G<lSFKLUkijiVVLma\G<n\I
:TU[G<lSFKLUijiVVLma\G<o\I
OWABCLnaULWABCVUU=<XOWABCUULWABCVijiVVcU=<XOWABCUULWABCVjpVVVI
:TULnaaqVLma\aL\I
:TULnr=<Xh=C<P<BUqmnVVLma\TKb\I
ObLC<?GASCG@B:=CK=ULVI
]]
#hich of the following will be included in the output 8tring
s
$ %&hoose all that
apply.'
(.
.e1
).
.e2
&.
=s
*.
fly
+. Aone of the above.
,. &ompilation fails.
2. (n e"ception is thrown at runtime.
(nswer:
B , C, and D are correct. Hemember, that the
equals()
method for the
integer wrappers
will only return
true
if the two primitive types and the two values are e7ual.
#ith C, it's
okay to unbo" and use
==
. ,or D, it's okay to create a wrapper object with an
e"pression,
and unbo" it for comparison with a primitive.
A, E, F, and G are incorrect based on the above. %Hemember that A is
using the
equals()
method to try to compare two di<erent types.' %/bjective F.5'
5PF2iven:
1. import java.text.*;
2. class DateOne {
3. public static void main(String[] args) {
4. Date d = new Date(1123631685981L);
5. DateFormat df = new DateFormat();
6. System.out.println(df.format(d));
7. }
8. }
(nd given that 550FGF5G4:?45D is the number of milliseconds between 9an.
5, 5?36, and
sometime on (ug. ?, 066:, what is the result$ %Aote: the time of day in option
( may vary.'
(. 4I?I6: :::1 ;>
).
1123631685981L
&. (n e"ception is thrown at runtime.
*. &ompilation fails due to a single error in the code.
+. &ompilation fails due to multiple errors in the code.
(nswer:
E is correct. The *ate class is located in the
java.util
package so it needs
an
import
, and
DateFormat
objects must be created using a static method such
as
DateFormat.getInstance()
or
DateFormat.getDateInstance().
A, B, C, and D are incorrect based on the above. %/bjective F.1'
68F2iven:
:?@ABCEF;FG:AGHI
JKFLLe<b^AFBQN]
@S^K:JJKFLLsA?@SC<B:?@K<?<=CLO<B:FK:tF^K<N
@B:;FC<e<b^AFBQua=<Xe<b^AFBQUVI
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
sA?@SC<BJa=<XsA?@SC<BUVI
JGLCAB<hCUJVI
]
;A:QLCAB<hCUsA?@SC<BJVN
CBbN
f^E<JCfSC@SCOCB<F?ALa=<Xf^E<JCfSC@SCOCB<F?U
=<XR:K<fSC@SCOCB<F?U\?bR:K<\VVI
ALGXB:C<f^E<JCUJVI
ALGJKAL<UVI
ObLC<?GASCG@B:=CK=U\QA=<\VI
]JFCJWUZ[J<@C:A=[VNObLC<?GASCG@B:=CK=U\<[J\VI]
]
]
#hat is the result$ %&hoose all that apply.'
(.
exc
).
done
&. &ompilation fails.
*. +"actly one object is seriali=ed.
+. +"actly two objects are seriali=ed.
(nswer:
A is correct. (n instance of type &omputer Jasa Keyboard. )ecause
Keyboard doesn't implement 8eriali=able, any attempt to seriali=e an instance
of &omputer will cause an e"ception to be thrown.
B, C, D, and E are incorrect based on the above. -f Keyboard did
implement 8eriali=able
then two objects would have been seriali=ed. %/bjective F.F'
6+F#hich will compile and run without e"ception$ %&hoose all that apply.'
(.
System.out.format("%b", 123);
).
System.out.format("%c", "x");
&.
System.out.printf("%d", 123);
*.
System.out.printf("%f", 123);
+.
System.out.printf("%d", 123.45);
,.
System.out.printf("%f", 123.45);
2.
System.out.format("%s", new Long("123"));
(nswer:
A , C, F, and G are correct. The
%b
%boolean' conversion character returns
true
for any
non
null
or nonboolean argument.
B is incorrect, the
%c
%character' conversion character e"pects a character,
not a 8tring. D is incorrect, the
%f
%Coatingpoint' conversion character won't
automatically promote an integer type. E is incorrect, the
%d
%integral'
conversion character won't take a Coatingpoint number. %Aote: The
format()
and
printf()
methods behave identically.' %/bjective F.:'
64F2iven:
JKFLLvAK:LWN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
:=C[ajI
OCB:=PwSTT<BL^a=<XOCB:=PwSTT<BU\GGT<QJ^F\VI
L^GQ<K<C<UixyVI
L^G:=L<BCUix\Ft\VI
:TUL^GK<=PCWUVzyV[aL^G:=Q<[fTU\^\VI
L^GQ<K<C<UU[giVxU[goVVI
ObLC<?GASCG@B:=CK=UL^VI
]
]
#hat is the result$
(.
.faza
).
.fzba
&.
..azba
*.
.fazba
+.
..fezba
,. &ompilation fails.
2. (n e"ception is thrown at runtime.
(nswer:
C is correct. Hemember that
StringBuffer
methods use =erobased
inde"es, and that
ending inde"es are typically e"clusive.
A, B, D, E, F, and G are incorrect based on the above.%/bjective F.5'
65FThe bottom line is this: if you want objects of your class to be used as keys
for a hashtable %or as elements in any data structure that uses e7uivalency for
searching forLandIor retrievingLan object', then you must override
equals()
so that two di<erent instances can be considered the same.
66F!emember that the
equals()
,
hashCode()
, and
toString()
methods are
all
public
. The following would not be a &alid o&erride of the
equals()
method, although it might appear to be if you dont look closely
enough during the e(am
class Foo { boolean equals(Object o) { } }
And watch out for the argument types as well. The following method
is an o&erload, but not an o&erride of the
equals()
method
class Boo { public boolean equals(Boo b) { } }
+e sure youre &ery comfortable with the rules of o&erriding so that
you can identify whether a method from ,b%ect is being o&erridden,
o&erloaded, or illegally redeclared in a class. The
equals()
method in
class +oo changes the argument from ,b%ect to +oo, so it becomes
an o&erloaded method and wont be called unless its from your own
code that knows about this new, di-erent method that happens to
also be named
equals()
.
69FYou can so easily mistake ./ollections. for ./ollection.)be
careful. 0eep in mind that /ollections is a class, with static utility
methods, while /ollection is an interface with declarations of the
methods common to most collections including
add()
,
remove()
,
contains()
,
size()
, and
iterator()
.
while Jash>ap lets you have
null
values as well as one
null
key, a Jashtable
doesn't let you have anything that's
null
.
The
Arrays.sort()
method is overridden in the same way the
Collections.sort()
method is.
Arrays.sort(arrayToSort)
Arrays.sort(arrayToSort, Comparator)
String [] sa = {"one", "two", "three", "four"};
Arrays.sort(sa);
The &ollections class and the (rrays class both provide methods that allow
you to search for a specifc element.#hen searching through collections or
arrays, the following rules apply:
8earches are performed using the
binarySearch()
method.
8uccessful searches return the
int
inde" of the element being searched.
Unsuccessful searches return an
int
inde" that represents the insertion
point.
The insertion point is the place in the collectionIarray where the element
would be inserted to keep the collectionIarray properly sorted. )ecause
positive return values and
0
indicate successful searches, the
binarySearch()
method uses negative numbers to indicate insertion points. 8ince
0
is a valid
result for a successful search, the frst available insertion point is
-1
.
Therefore, the actual insertion point is represented as %
-
%insertion point'
-1
'.
,or instance, if the insertion point of a search is at element
2
, the actual
insertion point returned will be
-3
.
The collectionIarray being searched must be sorted before you can search it.
-f you attempt to search an array or collection that has not already been
sorted, the results of the search will not be predictable.
-f the collectionIarray you want to search was sorted in natural order, it
must be searched in natural order. %This is accomplished by A/T sending a
&omparator as an argument to the
binarySearch()
method.'
-f the collectionIarray you want to search was sorted using a &omparator, it
must be searched using the same &omparator, which is passed as the second
argument to the
binarySearch()
method. Hemember that &omparators cannot
be used when searching arrays of primitives.
Converting Arra!s to "ists to Arra!s
There are a couple of methods that allow you to convert arrays to Dists, and
Dists to arrays. The Dist and 8et classes have
toArray()
methods, and the
(rrays class has a method called
asList()
. The
Arrays.asList()
method copies
an array into a Dist. The (;- says, !Heturns a f"edsi=e list backed by the
specifed array. %&hanges to the returned list 'write through' to the array.'!
#hen you use the
asList()
method, the array and the Dist become joined at
the hip. #hen you update one of them, the other gets updated automatically.
There's nothing too fancy going on with the
toArray()
methodB it comes in two
Cavors: one that returns a new /bject array, and one that uses the array you
send it as the destination array:
6:F
public void addAnimal(List<? extends Animal> animals)
)y saying
<? extends Animal>
, we're saying, !- can be assigned a collection
that is a subtype of Dist and typed for M(nimalN or anything that extends
(nimal. (nd oh yes, - 8#+(H that - will not (** anything into the collection.!
,irst, the
<? extends Animal>
means that you can take any subtype of
(nimalBhowever, that subtype can be +-TJ+H a subclass of a class %abstract or
concrete' /H a type that implements the interface after the word
extends
. -n
other words, the keyword
extends
in the conte"t of a wildcard represents
)/TJ subclasses and interface implementations. There is no
<? implements
Serializable>
synta". -f you want to declare a method that takes anything
that is of a type that implements 8eriali=able, you'd still use
extends
like this:
void foo(List<? extends Serializable> list) // odd, but correct
// to use "extends"
public void addAnimal(List<? super Dog> animals)
is essentially, !Jey
compiler, please accept any Dist with a generic type that is of type *og, or a
supertype of *og. Aothing lower in the inheritance tree can come in, but
anything higher than *og is /K.!
@ou probably already recogni=e why this works. -f you pass in a list of type
(nimal, then it's perfectly fne to add a *og to it. -f you pass in a list of type
*og, it's perfectly fne to add a *og to it. (nd if you pass in a list of type
/bject, it's 8T-DD fne to add a *og to it. #hen you use the
<? super ...>
synta", you are telling the compiler that you can accept the type on the right
hand side of
super
or any of its supertypes, sinceLand this is the key part
that makes it workLa collection declared as any supertype of *og will be able
to accept a *og as an element.
public void foo(List<?> list) { }
public void foo(List<Object> list) { }
-f there -8 a di<erence %and we're not yet saying there is', what is it$ There -8
a huge di<erence.
List<?>
, which is the wildcard
<?>
without the keywords
extends
or
super
, simply means !any type.! 8o that means any type of Dist can
be assigned to the argument. That could be a Dist of M*ogN, M-ntegerN,
M9)uttonN, M8ocketN, whatever. (nd using the wildcard alone, without the
keyword
super
%followed by a type', means that you cannot (** anything to
the list referred to as
List<?>
.
List<Object>
is completely di<erent from
List<?>
.
List<Object>
means that the
method can take /AD@ a
List<Object>
. Aot a
List<Dog>
, or a
List<Cat>
. -t does,
however, mean that you can add to the list, since the compiler has already
made certain that you're passing only a valid
List<Object>
into the method.
)y the way,
List<? extends Object>
and
List<?>
are absolutely identicalO They
both say, !- can refer to any type of object.!
1) List<?> list = new ArrayList<Dog>();
2) List<? extends Animal> aList = new ArrayList<Dog>();
3) List<?> foo = new ArrayList<? extends Animal>();
4) List<? extends Dog> cList = new ArrayList<Integer>();
5) List<? super Dog> bList = new ArrayList<Animal>();
6) List<? super Animal> dList = new ArrayList<Dog>();
The correct answers %the statements that compile' are 5, 0, and :.The three
that won't compile are
8tatement:
List<?> foo = new ArrayList<? extends Animal>();
;roblem: you cannot use wildcard notation in the object creation. 8o the
new
ArrayList<? extends Animal>()
will not compile.
8tatement:
List<? extends Dog> cList =new ArrayList<Integer>();
;roblem: @ou cannot assign an -nteger list to a reference that takes only a *og
%including any subtypes of *og, of course'.
8tatement:
List<? super Animal> dList = new ArrayList<Dog>();
;roblem: @ou cannot assign a *og to M$ super (nimalN. The *og is too !low!
in the class hierarchy. /nly M(nimalN or M/bjectN would have been legal.
JKFLL{=:?FK|AKQ<Brd<[C<=QL{=:?FKzNccSL<\d\:=LC<FQ AT\}\
dF=:?FKI
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
{=:?FK|AKQ<Br~APzQAP|AKQ<Ba=<X{=:?FK|AKQ<Br~APzUVIccfe
{=:?FK|AKQ<Brh=C<P<Bz[a=<X{=:?FK|AKQ<Brh=C<P<BzUVIccYf
]
]
:?@ABCEF;FGSC:KGHI
@S^K:JJKFLLsB<FC<{={BBFbk:LCN
@S^K:Jrdz;A:Q?Fu<{BBFbk:LCUdCVNccCFu<F=A^E<JCATF=
cc S=u=AX=Cb@<F=QSL<F
cc \d\CAB<@B<L<=CCW<Cb@<
k:LCrdzK:LCa=<X{BBFbk:LCrdzUVIcc=AXX<JF=JB<FC<CW<
cc K:LCSL:=P\d\
K:LCGFQQUCVI
]
]
-n the preceding code, if you invoke the
makeArrayList()
method with a *og
instance, the method will behave as though it looked like this all along:
public void makeArrayList(Dog t) {
List<Dog> list = new ArrayList<Dog>();
list.add(t);
}
The strangest thing about generic methods is that you must declare the type
variable )+,/H+ the return type of the method:
public <T> void makeArrayList(T t)
The MTN before
void
simply defnes what T is before you use it as a type in
the argument. @ou >U8T declare the type like that unless the type is specifed
for the class. -n &reate(n(rrayDist, the class is not generic, so there's no type
parameter placeholder we can use.
@ou're also free to put boundaries on the type you declare, for e"ample if you
want to restrict the
makeArrayList()
method to only Aumber or its subtypes
%-nteger, ,loat, and so on' you would say:
public <T extends Number> void
makeArrayList(T t)
,ne of the most common mistakes programmers make when creating
generic classes or methods is to use a 123 in the wildcard synta(
rather than a type &ariable 1T3, 143, and so on. This code might
look right, but isnt
public class NumberHolder<? extends Number> { }
'hile the 5uestion mark works when declaring a reference for a
&ariable, it does $,T work for generic class and method
declarations. This code is not legal
public class NumberHolder<?> { ? aNum; } // NO!
+ut if you replace the 123 with a legal identi6er, youre good
public class NumberHolder<T> { T aNum; } // Yes
6GF2iven:
:?@ABCEF;FGSC:KGHI
JKFLLd<LCN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
cc :=L<BCJAQ<W<B<
[GFQQU\A=<\VI
[GFQQU\CXA\VI
[GFQQU\df\VI
ObLC<?GASCG@B:=CK=U[G@AKKUVVI
]
]
#hich, inserted at
// insert code here
, will compile$ %&hoose all that apply.'
(.
List<String> x = new LinkedList<String>();
).
TreeSet<String> x = new TreeSet<String>();
&.
HashSet<String> x = new HashSet<String>();
*.
Queue<String> x = new PriorityQueue<String>();
+.
ArrayList<String> x = new ArrayList<String>();
,.
LinkedList<String> x = new LinkedList<String>();
(nswer:
D and F are correct. The
poll()
method is associated with Pueues. The
DinkedDist class
implements the Pueue interface.
A is incorrect because the Dist interface does not implement Pueue, and
the polymorphic instantiation would restrict
x
to invoking only those methods
declared in the Dist interface. B, C, and E are incorrect, based on the above.
%/bjective G.F'
6MF2iven:
@S^K:JLCFC:J;A:Q^<TAB<UVN
O<CL<Ca=<XdB<<O<CUVI
L<CGFQQU\o\VI
L<CGFQQUiVI
L<CGFQQU\n\VI
hC<BFCAB:CaL<CG:C<BFCABUVI
XW:K<U:CGWFLY<[CUVV
ObLC<?GASCG@B:=CU:CG=<[CUVm\\VI
]
#hich of the following statements are true$
(. The
before()
method will print
1 2
). The
before()
method will print
1 2 3
&. The
before()
method will print three numbers, but the order cannot be
determined.
*. The
before()
method will not compile.
+. The
before()
method will throw an e"ception at runtime.
(nswer:
E is correct. @ou can't put both 8trings and
int
s into the same Tree8et.
#ithout generics,
the compiler has no way of knowing what type is appropriate for this Tree8et,
so it allows everything to compile. (t runtime, the Tree8et will try to sort the
elements as they're added, and when it tries to compare an -nteger with a
8tring it will throw a &lass&ast+"ception. Aote that although the
before()
method does not use generics, it does use autobo"ing. #atch out for code
that uses some new features and some old features mi"ed together.
A, B, C, and D are incorrect based on the above. %/bjective G.:'
6PF2iven:
interface Hungry<E> { void munch(E x); }
interface Carnivore<E extends Animal> extends Hungry<E> {}
interface Herbivore<E extends Plant> extends Hungry<E> {}
abstract class Plant {}
class Grass extends Plant {}
abstract class Animal {}
class Sheep extends Animal implements Herbivore<Sheep> {
public void munch(Sheep x) {}
}
class Wolf extends Animal implements Carnivore<Sheep> {
public void munch(Sheep x) {}
}
#hich of the following changes %taken separately' would allow this code to
compile$
%&hoose all that apply.'
(. &hange the &arnivore interface to
interface Carnivore<E extends Plant> extends Hungry<E> {}
). &hange the Jerbivore interface to
interface Herbivore<E extends Animal> extends Hungry<E> {}
&. &hange the 8heep class to
class Sheep extends Animal implements Herbivore<Plant> {
public void munch(Grass x) {}
}
*. &hange the 8heep class to
class Sheep extends Plant implements Carnivore<Wolf> {
public void munch(Wolf x) {}
}
+. &hange the #olf class to
class Wolf extends Animal implements Herbivore<Grass> {
public void munch(Grass x) {}
}
,. Ao changes are necessary.
(nswer:
B is correct. The problem with the original code is that 8heep tries to
implement
Herbivore<Sheep>
and Jerbivore declares that its type parameter
E
can be any type that e"tends ;lant. 8ince a 8heep is not a ;lant,
Herbivore<Sheep>
makes no senseL the type 8heep is outside the allowed
range of Jerbivore's parameter
E
. /nly solutions that either alter the
defnition of a 8heep or alter the defnition of Jerbivore will be able to f" this.
8o A, E, and F are eliminated. B works, changing the defnition of an
Jerbivore to allow it to eat 8heep solves the problem. C doesn't work because
an
Herbivore<Plant>
must have a
munch(Plant)
method, not
munch(Grass)
. (nd
D doesn't work, because in D we made 8heep e"tend ;lant, now the #olf
class breaks because its
munch(Sheep)
method no longer fulflls the contract of
&arnivore. %/bjective G.1'
98F2iven that 8tring implements java.lang.&har8e7uence, and:
:?@ABCEF;FGSC:KGHI
@S^K:JJKFLLkA=PABQR:=Q<BN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
OCB:=P_`FBBFbaN\noi\x\noijyq\x\n\x\no\x\noijyqp\]I
k:LCrOCB:=PzK:LCa{BBFbLGFLk:LCUFBBFbVI
sAKK<JC:A=rOCB:=PzB<LSKCk:LCaP<CkA=PABQLUK:LCVI
]
cc hYOZd~Zsk{{dhfY|ZZ
N
sAKK<JC:A=rZzKA=PABQLa=<X{BBFbk:LCrZzUVI
TABUZXABQ>JAKKV
:TUXABQGK<=PCWUVzyVKA=PABQLGFQQUXABQVI
B<CSB=KA=PABQLI
]]
#hich declarations could be inserted at
// INSERT DECLARATION HERE
so that the
program
will compile and run$ %&hoose all that apply.'
(.
public static <E extends CharSequence> Collection<? extends CharSequence>
getLongWords(Collection<E> coll)
).
public static <E extends CharSequence> List<E> getLongWords(Collection<E>
coll)
&.
public static Collection<E extends CharSequence>
getLongWords(Collection<E> coll)
*.
public static List<CharSequence> getLongWords(Collection<CharSequence>
coll)
+.
public static List<? extends CharSequence> getLongWords(Collection<?
extends CharSequence> coll)
,.
static public <E extends CharSequence> Collection<E>
getLongWords(Collection<E> coll)
2.
static public <E super CharSequence> Collection<E>
getLongWords(Collection<E> coll)
(nswer:
F is correct.
A is close, but it's wrong because the return value is too vague. The last
line of the method e"pects the return value to be
Collection<String>
, not
Collection<? extends CharSequence>.
B is wrong because
longWords
has been
declared as a
Collection<E>
, and that can't be implicitly converted to a
List<E>
to match the declared return value. %+ven though we know that
longWords
is
really an
ArrayList<E>
, the compiler only know what it's been declared as.' C,
D, and E are wrong because they do not declare a type variable + %there's no
MN before the return value' so the
getLongWords()
method body will not
compile. G is wrong because
E super CharSequence
makes no senseL
super
could be used in conjunction with a
wildcard but not a type variable like
E
. %/bjective G.F'
9+F2iven a method declared as:
public static <E extends Number> List<? super E> process(List<E> nums)
( programmer wants to use this method like this:
// INSERT DECLARATIONS HERE
output = process(input);
#hich pairs of declarations could be placed at
// INSERT DECLARATIONS HERE
to
allow
the code to compile$ %&hoose all that apply.'
(.
ArrayList<Integer> input = null;
ArrayList<Integer> output = null;
).
ArrayList<Integer> input = null;
List<Integer> output = null;
&.
ArrayList<Integer> input = null;
List<Number> output = null;
*.
List<Number> input = null;
ArrayList<Integer> output = null;
+.
List<Number> input = null;
List<Number> output = null;
,.
List<Integer> input = null;
List<Integer> output = null;
2. Aone of the above.
(nswer:
B, E, and F are correct.
The return type of process is defnitely declared as a
List
, not an
ArrayList
,
so A and D are wrong. C is wrong because the return type evaluates to
List<Integer>
, and that can't be assigned to a variable of type
List<Number>
. /f
course all these would probably cause a
NullPointerException
since the
variables are still nullLbut the 7uestion only asked us to get the code to
compile.
94FJere's a 7uick summary of the di<erences between inner class
instantiation code that's within the outer class %but not
static
', and inner
class instantiation code that's outside the outer class:
,rom inside the outer class instance code, use the inner class name in the
normal way:
MyInner mi = new MyInner();
,rom outside the outer class instance code %including static method code
within the outer class', the inner class name must now include the outer
class's name:
MyOuter.MyInner
To instantiate it, you must use a reference to the outer class:
new MyOuter().new MyInner(); or outerObjRef.new MyInner();
if you already have an instance of the outer class.
the rules for an inner class referencing itself or the outer instance are as
follows:
To reference the inner class instance itself, from within the inner class code,
use
this
.
To reference the !outer
this
! %the outer class instance' from within the inner
class code, use
NameOfOuterClass.this
%e"ample,
MyOuter.this
'.
A method-local inner class can be instantiated only within the method where
the inner class is defned. -n other words, no other code running in any other
methodLinside or outside the outer classLcan ever instantiate the method
local inner class. Dike regular inner class objects, the methodlocal inner class
object shares a special relationship with the enclosing %outer' class object,
and can access its
private
%or any other' members. Jowever, the inner class
object cannot use the local variables of the method the inner class is in.
Think about it. The local variables of the method live on the stack, and e"ist
only for the lifetime of the method. @ou already know that the scope of a local
variable is limited to the method the variable is declared in. #hen the method
ends, the stack frame is blown away and the variable is history. )ut even after
the method completes, the inner class object created within it might still be
alive on the heap if, for e"ample, a reference to it was passed into some other
code and then stored in an instance variable. )ecause the local variables
aren't guaranteed to be alive as long as the methodlocal inner class object,
the inner class object can't use them. Unless the local variables are marked
final

JKFLLMbfSC<BoN
@B:;FC<OCB:=P[a\fSC<Bo\I
;A:QQAOCSTTUVN
OCB:=Pta\KAJFK;FB:F^K<\I
JKFLLMbh==<BN
@S^K:J;A:QL<<fSC<BUVN
ObLC<?GASCG@B:=CK=U\fSC<B[:L\m[VI
ObLC<?GASCG@B:=CK=U\kAJFK;FB:F^K<t:L\mtVIccA=CsA?@:K<
]ccJKAL<:==<BJKFLL?<CWAQ
]ccJKAL<:==<BJKFLLQ<T:=:C:A=
]ccJKAL<ASC<BJKFLL?<CWAQQAOCSTTUV
]ccJKAL<ASC<BJKFLL
(nd just a reminder about modifers within a method: the same rules apply to
methodlocal inner classes as to local variable declarations. @ou can't, for
e"ample, mark a methodlocal inner class
public
,
private
,
protected
,
static
,
transient
, and the like. The only modifers you can apply to a methodlocal
inner class are
abstract
and
final
, but as always, never both at the same
time.
95F2iven:
1. class Foo {
2. class Bar{ }
3. }
4. class Test {
5. public static void main(String[] args) {
6. Foo f = new Foo();
7. // Insert code here
8. }
9. }
#hich, inserted at line 3, creates an instance of )ar$ %&hoose all that apply.'
(.
Foo.Bar b = new Foo.Bar();
).
Foo.Bar b = f.new Bar();
&.
Bar b = new f.Bar();
*.
Bar b = f.new Bar();
+.
Foo.Bar b = new f.Bar();
Answer#
B is correct because the synta" is correctLusing both names %the enclosing
class and the inner class' in the reference declaration, then using a reference
to the enclosing class to invoke
new
on the inner class.
A, C, D, and E all use incorrect synta". A is incorrect because it doesn't
use a reference to the enclosing class, and also because it includes both
names in the call to
new
. C is incorrect because it doesn't use the enclosing
class name in the reference variable declaration, and because the
new
synta"
is wrong. D is incorrect because it doesn't use the enclosing class name in the
reference variable declaration. E is incorrect because the
new
synta" is wrong.
96F#hich are true about a methodlocal inner class$ %&hoose all that apply.'
(. -t must be marked
final.
). -t can be marked
abstract
.
&. -t can be marked
public
.
*. -t can be marked
static
.
+. -t can access private members of the enclosing class.
Answer#
B and E. B is correct because a methodlocal inner class can be
abstract
,
although it means a subclass of the inner class must be created if the
abstract
class is to be used %so an
abstract
methodlocal inner class is probably not
useful'. E is correct because a methodlocal inner class works like any other
inner classLit has a special relationship to an instance of the enclosing class,
thus it can access all members of the enclosing class.
A is incorrect because a methodlocal inner class does not have to be
declared
final
%although it is legal to do so'. C and D are incorrect because a
methodlocal inner class cannot be made
public
%rememberLlocal variables
can't be
public
' or
static
.
99FHemember the following key points about locking and synchroni=ation:
/nly methods %or blocks' can be
synchronized
, not variables or classes.
+ach object has just one lock.
Aot all methods in a class need to be synchroni=ed. ( class can have both
synchronized
and non
synchronized
methods.
-f two threads are about to e"ecute a
synchronized
method in a class, and
both threads are using the same instance of the class to invoke the method,
only one thread at a time will be able to e"ecute the method. The other thread
will need to wait until the frst one fnishes its method call. -n other words,
once a thread ac7uires the lock on an object, no other thread can enter any of
the synchroni=ed methods in that class %for that object'.
-f a class has both
synchronized
and non
synchronized
methods, multiple
threads can still access the class's non
synchronized
methodsO -f you have
methods that don't access the data you're trying to protect, then you don't
need to synchroni=e them. 8ynchroni=ation can cause a hit in some cases %or
veven deadlock if used incorrectly', so you should be careful not to overuse it.
-f a thread goes to sleep, it holds any locks it hasLit doesn't release them.
( thread can ac7uire more than one lock. ,or e"ample, a thread can enter a
synchronized
method, thus ac7uiring a lock, and then immediately invoke a
synchronized
method on a di<erent object, thus ac7uiring that lock as well. (s
the stack unwinds, locks are released again. (lso, if a thread ac7uires a lock
and then attempts to call a
synchronized
method on that same
object, no problem. The 9Q> knows that this thread already has the lock for
this object, so the thread is free to call other
synchronized
methods on the
same object, using the lock the thread already has.
@ou can synchroni=e a block of code rather than a method.
So $at A%out Static &etods' Can (e! Be S!ncroni)ed'
static
methods can be
synchronized
. There is only one copy of the static data
you're trying to protect, so you only need one lock per class to synchroni=e
static methodsLa lock for the whole class. There is such a lockB every class
loaded in 9ava has a corresponding instance of java.lang.&lass representing
that class. -t's that java.lang.&lass instance whose lock is used to protect the
static
methods of the class %if they're
synchronized
'. There's nothing special
you have to do to synchroni=e a
static
method:
public static synchronized int getCount() {
return count;
}
(gain, this could be replaced with code that uses a
synchronized
block. -f the
method is defned in a class called >y&lass, the e7uivalent code is as follows:
public static int getCount() {
synchronized(MyClass.class) {
return count;
}
}
#aitLwhat's that
MyClass.class
thing$ That's called a class literal. -t's a
special feature in the 9ava language that tells the compiler %who tells the 9Q>':
go and fnd me the instance of &lass that represents the class called >y&lass.
@ou can also do this with the following code:
public static void classMethod() {
Class cl = Class.forName("MyClass");
synchronized (cl) {
// do stuff
}
}
9:Fwait!"# notify!"# and notifyAll!" must be called from within a synchroni$ed
context A thread can%t invoke a wait or notify method on an object unless it
owns that object%s lock.
The methods
wait()
,
notify()
, and
notifyAll()
are methods of only
%a&a.lang.,b%ect, not of %a&a.lang.Thread or %a&a.lang.!unnable. +e
sure you know which methods are de6ned in Thread, which in ,b%ect,
and which in !unnable (%ust
run()
, so thats an easy one). ,f the key
methods in Thread, be sure you know which are
static
)
sleep()
and
yield()
, and which are not
static
)
join()
and
start()
.
9GF2iven the following
@S^K:JJKFLLF:Cd<LCN
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
ObLC<?GASCG@B:=CU\n\VI
Lb=JWBA=:t<QUFBPLVN
ObLC<?GASCG@B:=CU\o\VI
CBbN
FBPLGXF:CUVI
]
JFCJWUh=C<BBS@C<QZ[J<@C:A=<VN]
]
ObLC<?GASCG@B:=CU\i\VI
]
]#hat is the result of trying to compile and run this program$
(. -t fails to compile because the
IllegalMonitorStateException
of
wait()
is not
dealt
with in line 3.
).
1 2 3
&.
1 3
*.
1 2
+. (t runtime, it throws an
IllegalMonitorStateException
when trying to wait.
,. -t will fail to compile because it has to be synchroni=ed on the
this
object.
(nswer:
D is correct. 5 and 0 will be printed, but there will be no return from the
wait
call because
no other thread will notify the main thread, so F will never be printed. -t's
fro=en at line 3.
A is incorrectB
IllegalMonitorStateException
is an unchecked e"ception. B
and C are incorrectB F will never be printed, since this program will wait
forever. E is incorrect because
IllegalMonitorStateException
will never be
thrown because the
wait()
is done on
args
within a block of code
synchroni=ed on
args
. F is incorrect because any object can be used to
synchroni=e on and
this
and
static
don't mi". %/bjective 1.1'
9MF2iven:
@S^K:JLCFC:JLb=JWBA=:t<Q;A:Q?F:=UOCB:=P_`FBPLVCWBAXL
h=C<BBS@C<QZ[J<@C:A=N
dWB<FQCa=<XdWB<FQUVI
CGLCFBCUVI
ObLC<?GASCG@B:=CU\\VI
CGXF:CUnVI
ObLC<?GASCG@B:=CU\\VI
]
#hat is the result of this code$
(. -t prints
X
and e"its.
). -t prints
X
and never e"its.
&. -t prints
XY
and e"its almost immeditately.
*. -t prints
XY
with a 56second delay between
X
and
Y
.
+. -t prints
XY
with a 56666second delay between
X
and
Y
.
,. The code does not compile.
2. (n e"ception is thrown at runtime.
(nswer:
G is correct. The code does not ac7uire a lock on
t
before calling
t.wait()
,
so it throws an
IllegalThreadStateException
. The method is
synchronized
, but
it's not synchroni=ed on
t
so the e"ception will be thrown. -f the wait were
placed inside a
synchronized(t)
block, then the answer would have been D.
A, B, C, D, E, and F are incorrect based the logic described above.
%/bjective 1.0'
9PF=iven!
@S^K:JJKFLLdWB<FQ~<?AN
Lb=JWBA=:t<Q;A:QFUVNFJCwSLbUVI]
LCFC:JLb=JWBA=:t<Q;A:Q^UVNFJCwSLbUVI]
LCFC:J;A:QFJCwSLbUVN
CBbNdWB<FQGLK<<@UnVI]
JFCJWUh=C<BBS@C<QZ[J<@C:A=<VN]
]
@S^K:JLCFC:J;A:Q?F:=UOCB:=P_`FBPLVN
T:=FKdWB<FQ~<?A[a=<XdWB<FQ~<?AUVI
T:=FKdWB<FQ~<?Aba=<XdWB<FQ~<?AUVI
S==F^K<BS==F^K<a=<XS==F^K<UVN
@S^K:J;A:QBS=UVN
:=CA@C:A=aU:=CVUMFCWGBF=QA?UVHjVI
LX:CJWUA@C:A=VN
JFL<>[GFUVI^B<FuI
JFL<n>[G^UVI^B<FuI
JFL<o>bGFUVI^B<FuI
JFL<i>bG^UVI^B<FuI
]]
]I
dWB<FQCWB<FQna=<XdWB<FQUBS==F^K<VI
dWB<FQCWB<FQoa=<XdWB<FQUBS==F^K<VI
CWB<FQnGLCFBCUVI
CWB<FQoGLCFBCUVI
]]
#hich of the following pairs of method invocations could A+Q+H be e"ecuting
at the same
time$ %&hoose all that apply.'
(.
x.a() in thread1,
and
x.a() in thread2
).
x.a() in thread1,
and
x.b() in thread2
&.
x.a() in thread1,
and
y.a() in thread2
*.
x.a() in thread1,
and
y.b() in thread2
+.
x.b() in thread1,
and
x.a() in thread2
,.
x.b() in thread1,
and
x.b() in thread2
2.
x.b() in thread1,
and
y.a() in thread2
J.
x.b() in thread1,
and
y.b() in thread2
(nswer:
A , F and *. A is incorrect because
synchronized
instance methods called
on the same instance, block each other. F and * could not happen because
synchronized static
methods in the same class block each other, regardless of
which instance was used to call the methods. %(n instance is not re7uired to
call
static
methodsB only the class.'
C could happen because
synchronized
instance methods called on di<erent
instances do not block each other. B, D, E, and G could all happen because
instance methods and
static
methods lock on di<erent objects, and do not
block each other. %/bjective 1.F'
:8Fa couple of rules for using static imports:
@ou must say
import static
B you can't say
static import
.
#atch out for ambiguously named
static
members. ,or instance, if you do
a static import for both the
Integer
class and the
Long
class, referring to
MAX_VALUE
will cause a compiler error, since both
Integer
and
Long
have a
MAX_VALUE
constant, and 9ava won't know which
MAX_VALUE
you're referring to.
@ou can do a static import on
static
object references, constants
%remember they're
static
and
final
', and
static
methods.
:+Fwhich of the followin% statements is tureV
, -n an assert statement, the e*pression after the colon(!) can
be any Java e*pression.
/ -f a switch block has no default, addin% an assert default is
considered appropriate.
; -n an assert statement, if the e*pression after the colon(! )
doe not have a value, the assertLs error messa%e will be empty.
< -t is appropriate to handle assertion failures usin% a catch
clause.
?*planation!
/ is correct. , is incorrect because only Jave e*pressions that
return a value can be used. Hor e*ample, a method that returns
void is ille%al. ; is incorrect because the e*pression after the
colon must have a value.
:4F,ssumin% that an interrupted e*ception has C@T been thrown and
that \a7iveThread] is a runnable thread, which three %uarantee
that a thread will leave the runnin% stateV
, yield() / wait() ; notify() < notify,ll()
? sleep(+888) H a7iveThread.$oin() = Thread.killThread()
/,?,H is correct. , is incorret, the yield() method is not
%uaranteed to cause a thread to leave the runnin% state, althou%h
if there are runnabel threads of the same priority as the
currently runnin% thread, then the current thread will probably
leave the runnin% state.
:5FBhich instantiation creates the ti%htest couplin%V
, /io<iesel b+ D new /io<iesel();
/ /io<iesel b+ D new /io<iesel(new (trin%(\canola]);
; /io<iesel b+ D new /io<iesel(new -nte%er(64));
< /io<iesel b+ D new /io<iesel(new Aiscosity());
< is correct, this instantiation re&uires that /io<iesel knows
somethin%s about Aiscosity class.
:6F:9F::F:GF:MF:PFG8FG+FG4F55F

You might also like