📄 tij0050.html
字号:
prt("<font color="#0000ff">byte</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">void</font> testShort() {
<font color="#0000ff">short</font> x = 0;
prt("<font color="#0000ff">short</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">void</font> testInt() {
<font color="#0000ff">int</font> x = 0;
prt("<font color="#0000ff">int</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">void</font> testLong() {
<font color="#0000ff">long</font> x = 0;
prt("<font color="#0000ff">long</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">void</font> testFloat() {
<font color="#0000ff">float</font> x = 0;
prt("<font color="#0000ff">float</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">void</font> testDouble() {
<font color="#0000ff">double</font> x = 0;
prt("<font color="#0000ff">double</font> argument:");
f1(x);f2(x);f3(x);f4(x);f5(x);f6(x);f7(x);
}
<font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> main(String[] args) {
PrimitiveOverloading p =
<font color="#0000ff">new</font> PrimitiveOverloading();
p.testConstVal();
p.testChar();
p.testByte();
p.testShort();
p.testInt();
p.testLong();
p.testFloat();
p.testDouble();
}
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">If
you view the output of this program, you’ll see that the constant value 5
is treated as an
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>int</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
so if an overloaded method is available that takes an
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>int</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
it is used. In all other cases, if you have a data type that is smaller than
the argument in the method, that data type is promoted.
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>char</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
produces a slightly different effect, since if it doesn’t find an exact
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>char</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
match, it is promoted to
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>int</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">What
happens if your argument is
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>bigger</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
than the argument expected by the overloaded method? A modification of the
above program gives the answer:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#009900">//: Demotion.java</font>
<font color="#009900">// Demotion of primitives and overloading</font>
<font color="#0000ff">public</font> <font color="#0000ff">class</font> Demotion {
<font color="#0000ff">static</font> <font color="#0000ff">void</font> prt(String s) {
System.out.println(s);
}
<font color="#0000ff">void</font> f1(<font color="#0000ff">char</font> x) { prt("f1(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">byte</font> x) { prt("f1(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">short</font> x) { prt("f1(<font color="#0000ff">short</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">int</font> x) { prt("f1(<font color="#0000ff">int</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">long</font> x) { prt("f1(<font color="#0000ff">long</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">float</font> x) { prt("f1(<font color="#0000ff">float</font>)"); }
<font color="#0000ff">void</font> f1(<font color="#0000ff">double</font> x) { prt("f1(<font color="#0000ff">double</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">char</font> x) { prt("f2(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">byte</font> x) { prt("f2(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">short</font> x) { prt("f2(<font color="#0000ff">short</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">int</font> x) { prt("f2(<font color="#0000ff">int</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">long</font> x) { prt("f2(<font color="#0000ff">long</font>)"); }
<font color="#0000ff">void</font> f2(<font color="#0000ff">float</font> x) { prt("f2(<font color="#0000ff">float</font>)"); }
<font color="#0000ff">void</font> f3(<font color="#0000ff">char</font> x) { prt("f3(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f3(<font color="#0000ff">byte</font> x) { prt("f3(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f3(<font color="#0000ff">short</font> x) { prt("f3(<font color="#0000ff">short</font>)"); }
<font color="#0000ff">void</font> f3(<font color="#0000ff">int</font> x) { prt("f3(<font color="#0000ff">int</font>)"); }
<font color="#0000ff">void</font> f3(<font color="#0000ff">long</font> x) { prt("f3(<font color="#0000ff">long</font>)"); }
<font color="#0000ff">void</font> f4(<font color="#0000ff">char</font> x) { prt("f4(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f4(<font color="#0000ff">byte</font> x) { prt("f4(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f4(<font color="#0000ff">short</font> x) { prt("f4(<font color="#0000ff">short</font>)"); }
<font color="#0000ff">void</font> f4(<font color="#0000ff">int</font> x) { prt("f4(<font color="#0000ff">int</font>)"); }
<font color="#0000ff">void</font> f5(<font color="#0000ff">char</font> x) { prt("f5(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f5(<font color="#0000ff">byte</font> x) { prt("f5(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f5(<font color="#0000ff">short</font> x) { prt("f5(<font color="#0000ff">short</font>)"); }
<font color="#0000ff">void</font> f6(<font color="#0000ff">char</font> x) { prt("f6(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> f6(<font color="#0000ff">byte</font> x) { prt("f6(<font color="#0000ff">byte</font>)"); }
<font color="#0000ff">void</font> f7(<font color="#0000ff">char</font> x) { prt("f7(<font color="#0000ff">char</font>)"); }
<font color="#0000ff">void</font> testDouble() {
<font color="#0000ff">double</font> x = 0;
prt("<font color="#0000ff">double</font> argument:");
f1(x);f2((<font color="#0000ff">float</font>)x);f3((<font color="#0000ff">long</font>)x);f4((<font color="#0000ff">int</font>)x);
f5((<font color="#0000ff">short</font>)x);f6((<font color="#0000ff">byte</font>)x);f7((<font color="#0000ff">char</font>)x);
}
<font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> main(String[] args) {
Demotion p = <font color="#0000ff">new</font> Demotion();
p.testDouble();
}
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Here,
the methods take narrower primitive values. If your argument is wider then you
must <A NAME="Index280"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>cast</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
to the necessary type using the type name in parentheses. If you don’t do
this, the compiler will issue an error message.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">You
should be aware that this is a <A NAME="Index281"></A><A NAME="Index282"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>narrowing
conversion,
</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
which means you might lose information during the cast. This is why the
compiler forces you to do it – to flag the narrowing conversion.
</FONT><a name="_Toc408018480"></a><P></DIV>
<A NAME="Heading142"></A><H3 ALIGN=LEFT>
Overloading
on return values
<P><A NAME="Index283"></A><A NAME="Index284"></A></H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">It
is common to wonder “Why only class names and method argument lists? Why
not distinguish between methods based on their return values?” For
example, these two methods, which have the same name and arguments, are easily
distinguished from each other:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#0000ff">void</font> f() {}
<font color="#0000ff">int</font> f() {} </PRE></font><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">This
works fine when the compiler can unequivocally determine the meaning from the
context, as in
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>int
x = f( )
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
However, you can call a method and ignore the return value; this is often
referred to as
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>calling
a method for its <A NAME="Index285"></A>side
effect
</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
since you don’t care about the return value but instead want the other
effects of the method call. So if you call the method this way:
</FONT><P></DIV><DIV ALIGN=LEFT><TT><FONT FACE="Courier New" SIZE=3 COLOR="Black">f();</FONT></TT><P></DIV><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">how
can Java determine which
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>f( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
should be called? And how could someone reading the code see it? Because of
this sort of problem, you cannot use return value types to distinguish
overloaded methods.
</FONT><a name="_Toc375545279"></a><a name="_Toc408018481"></a><P></DIV>
<A NAME="Heading143"></A><H3 ALIGN=LEFT>
Default
constructors
</H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">As
mentioned previously, a default constructor <A NAME="Index286"></A><A NAME="Index287"></A>is
one without arguments, used to create a “vanilla object.” If you
create a class that has no constructors, the compiler will automatically create
a default constructor for you. For example:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#009900">//: DefaultConstructor.java</font>
<font color="#0000ff">class</font> Bird {
<font color="#0000ff">int</font> i;
}
<font color="#0000ff">public</font> <font color="#0000ff">class</font> DefaultConstructor {
<font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> main(String[] args) {
Bird nc = <font color="#0000ff">new</font> Bird(); <font color="#009900">// default!</font>
}
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">The
line
</FONT><P></DIV><DIV ALIGN=LEFT><TT><FONT FACE="Courier New" SIZE=3 COLOR="Black">new
Bird();
</FONT></TT><P></DIV><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">creates
a new object and calls the default constructor, even though one was not
explicitly defined. Without it we would have no method to call to build our
object. However, if you define any constructors (with or without arguments),
the compiler will
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>not</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
synthesize one for you:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#0000ff">class</font> Bush {
Bush(<font color="#0000ff">int</font> i) {}
Bush(<font color="#0000ff">double</font> d) {}
}</PRE></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Now
if you say:
</FONT><P></DIV><DIV ALIGN=LEFT><TT><FONT FACE="Courier New" SIZE=3 COLOR="Black">new
Bush();
</FONT></TT><P></DIV><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">the
compiler will complain that it cannot find a constructor that matches.
It’s as if when you don’t put in any constructors, the compiler
says “You are bound to need
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>some</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
constructor, so let me make one for you.” But if you write a constructor,
the compiler says “You’ve written a constructor so you know what
you’re doing; if you didn’t put in a default it’s because you
meant to leave it out.”
</FONT><a name="_Toc375545280"></a><a name="_Toc408018482"></a><P></DIV>
<A NAME="Heading144"></A><H3 ALIGN=LEFT>
The
<A NAME="Index288"></A>this
keyword
</H3>
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">If
you have two objects of the same type called
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>a</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>b</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
you might wonder how it is that you can call a method
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>f( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
for both those objects:
</FONT><P></DIV>
<font color="#990000"><PRE><font color="#0000ff">class</font> Banana { <font color="#0000ff">void</font> f(<font color="#0000ff">int</font> i) { <font color="#009900">/* ... */</font> } }
Banana a = <font color="#0000ff">new</font> Banana(), b = <font color="#0000ff">new</font> Banana();
a.f(1);
b.f(2);</PRE></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">If
there’s only one method called
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>f( )</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
how can that method know whether it’s being called for the object
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>a</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
or
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>b</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">?
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">To
allow you to write the code in a convenient object-oriented syntax in which you
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -