⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tij312.htm

📁 这也是我们java老师给我们的thinking in java的一些资料
💻 HTM
📖 第 1 页 / 共 5 页
字号:
} <font color=#009900>///:~</font></PRE></FONT></BLOCKQUOTE><p><br></p>
<p><a name="_Toc305593310"></a><a name="_Toc305628782"></a>In <b>main(&#160;)</b> an array <b>petTypes </b>of <b>Class</b> objects is created using <b>Class.forName(&#160;)</b>. Since the <b>Pet</b> objects are in package <b>c09</b>, the package name must be used when naming the classes. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]A0489" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>Next, the <b>pets</b> array is filled by randomly indexing into <b>petTypes </b>and using the selected <b>Class</b> object to generate a new instance of that class with <b>Class.newInstance(&#160;)</b>, which uses the default (no-arg) class constructor to generate the new object. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]A0490" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>Both <b>forName(&#160;)</b> and <b>newInstance(&#160;)</b> can generate exceptions, which you can see handled in the <b>catch</b> clauses following the <b>try</b> block. Again, the names of the exceptions are relatively useful explanations of what went wrong (<b>IllegalAccessException</b> relates to a violation of the Java security mechanism). <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]A0491" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>After creating the <b>AssociativeArray</b>, it is filled with key-value pairs of pet names and <b>Counter</b> objects. Then each <b>Pet</b> in the randomly-generated array is tested and counted using <b>instanceof</b>. The array and <b>AssociativeArray</b> are printed so you can compare the results. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]A0492" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>There&#146;s a rather narrow restriction on <b>instanceof</b>: You can compare it to a named type only, and not to a <b>Class</b> object. In the preceding example you might feel that it&#146;s tedious to write out all of those <b>instanceof</b> expressions, and you&#146;re right. But there is no way to cleverly automate <b>instanceof </b>by creating an array of <b>Class</b> objects and comparing it to those instead (stay tuned&#151;you&#146;ll see an alternative). This isn&#146;t as great a restriction as you might think, because you&#146;ll eventually understand that your design is probably flawed if you end up writing a lot of <b>instanceof</b> expressions. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]Chap12_1850" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>Of course, this example is contrived&#151;you&#146;d probably put a <b>static</b> field in each type and increment it in the constructor to keep track of the counts. You would do something like that <i>if</i> you had control of the source code for the class and could change it. Since this is not always the case, RTTI can come in handy. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]Chap12_1851" title="Send BackTalk Comment">Feedback</a></font><br></p>
<h4>
<a name="Heading9795"></a>Using class literals</h4>
<p>It&#146;s interesting to see how the <b>PetCount.java</b> example can be rewritten using class literals. The result is cleaner in many ways:<br></p>

<BLOCKQUOTE><FONT SIZE = "+1"><PRE><font color=#009900>//: c10:PetCount2.java</font>
<font color=#009900>// Using class literals.</font>
<font color=#0000ff>package</font> c10;
<font color=#0000ff>import</font> com.bruceeckel.simpletest.*;
<font color=#0000ff>import</font> java.util.*;

<font color=#0000ff>public</font> <font color=#0000ff>class</font> PetCount2 {
  <font color=#0000ff>private</font> <font color=#0000ff>static</font> Test monitor = <font color=#0000ff>new</font> Test();
  <font color=#0000ff>private</font> <font color=#0000ff>static</font> Random rand = <font color=#0000ff>new</font> Random();
  <font color=#0000ff>public</font> <font color=#0000ff>static</font> <font color=#0000ff>void</font> main(String[] args) {
    Object[] pets = <font color=#0000ff>new</font> Object[15];
    Class[] petTypes = {
      <font color=#009900>// Class literals:</font>
      Pet.<font color=#0000ff>class</font>,
      Dog.<font color=#0000ff>class</font>,
      Pug.<font color=#0000ff>class</font>,
      Cat.<font color=#0000ff>class</font>,
      Rodent.<font color=#0000ff>class</font>,
      Gerbil.<font color=#0000ff>class</font>,
      Hamster.<font color=#0000ff>class</font>,
    };
    <font color=#0000ff>try</font> {
      <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++) {
        <font color=#009900>// Offset by one to eliminate Pet.class:</font>
        <font color=#0000ff>int</font> rnd = 1 + rand.nextInt(petTypes.length - 1);
        pets[i] = petTypes[rnd].newInstance();
      }
    } <font color=#0000ff>catch</font>(InstantiationException e) {
      System.out.println(<font color=#004488>"Cannot instantiate"</font>);
      System.exit(1);
    } <font color=#0000ff>catch</font>(IllegalAccessException e) {
      System.out.println(<font color=#004488>"Cannot access"</font>);
      System.exit(1);
    }
    AssociativeArray map =
      <font color=#0000ff>new</font> AssociativeArray(petTypes.length);
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; petTypes.length; i++)
      map.put(petTypes[i].toString(), <font color=#0000ff>new</font> Counter());
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++) {
      Object o = pets[i];
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Pet)
        ((Counter)map.get(<font color=#004488>"class c10.Pet"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Dog)
        ((Counter)map.get(<font color=#004488>"class c10.Dog"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Pug)
        ((Counter)map.get(<font color=#004488>"class c10.Pug"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Cat)
        ((Counter)map.get(<font color=#004488>"class c10.Cat"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Rodent)
        ((Counter)map.get(<font color=#004488>"class c10.Rodent"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Gerbil)
        ((Counter)map.get(<font color=#004488>"class c10.Gerbil"</font>)).i++;
      <font color=#0000ff>if</font>(o <font color=#0000ff>instanceof</font> Hamster)
        ((Counter)map.get(<font color=#004488>"class c10.Hamster"</font>)).i++;
    }
    <font color=#009900>// List each individual pet:</font>
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++)
      System.out.println(pets[i].getClass());
    <font color=#009900>// Show the counts:</font>
    System.out.println(map);
    monitor.expect(<font color=#0000ff>new</font> Object[] {
      <font color=#0000ff>new</font> TestExpression(<font color=#004488>"%% class c10\\."</font> +
        <font color=#004488>"(Dog|Pug|Cat|Rodent|Gerbil|Hamster)"</font>,
        pets.length),
      <font color=#0000ff>new</font> TestExpression(<font color=#004488>"%% class c10\\."</font> +
        <font color=#004488>"(Pet|Dog|Pug|Cat|Rodent|Gerbil|Hamster) : \\d+"</font>,
        petTypes.length)
    });
  }
} <font color=#009900>///:~</font></PRE></FONT></BLOCKQUOTE><p><br></p>
<p>Here, the <b>typenames</b> array has been removed in favor of getting the type name strings from the <b>Class</b> object. Notice that the system can distinguish between classes and interfaces. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]Chap12_1852" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>You can also see that the creation of <b>petTypes</b> does not need to be surrounded by a <b>try</b> block since it&#146;s evaluated at compile time and thus won&#146;t throw any exceptions, unlike <b>Class.forName(&#160;)</b>. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]Chap12_1853" title="Send BackTalk Comment">Feedback</a></font><br></p>
<p>When the <b>Pet</b> objects are dynamically created, you can see that the random number is restricted so it is between one and <b>petTypes.length</b> and does not include zero. That&#146;s because zero refers to <b>Pet.class</b>, and presumably a generic <b>Pet</b> object is not interesting. However, since <b>Pet.class</b> is part of <b>petTypes</b>, the result is that all of the pets get counted. <font size="-2"><a href="mailto:TIJ3@MindView.net?Subject=[TIJ3]Chap12_1854" title="Send BackTalk Comment">Feedback</a></font><br></p>
<h4>
<a name="Heading9871"></a>A dynamic <b>instanceof</b><br></h4>
<p><a name="Index911"></a>The <b>Class.isInstance</b><a name="Index912"></a><a name="Index913"></a><a name="Index914"></a> method provides a way to dynamically call the <b>instanceof</b> operator. Thus, all those tedious <b>instanceof</b> statements can be removed in the <b>PetCount</b> example:<br></p>

<BLOCKQUOTE><FONT SIZE = "+1"><PRE><font color=#009900>//: c10:PetCount3.java</font>
<font color=#009900>// Using isInstance()</font>
<font color=#0000ff>package</font> c10;
<font color=#0000ff>import</font> com.bruceeckel.simpletest.*;
<font color=#0000ff>import</font> java.util.*;

<font color=#0000ff>public</font> <font color=#0000ff>class</font> PetCount3 {
  <font color=#0000ff>private</font> <font color=#0000ff>static</font> Test monitor = <font color=#0000ff>new</font> Test();
  <font color=#0000ff>private</font> <font color=#0000ff>static</font> Random rand = <font color=#0000ff>new</font> Random();
  <font color=#0000ff>public</font> <font color=#0000ff>static</font> <font color=#0000ff>void</font> main(String[] args) {
    Object[] pets = <font color=#0000ff>new</font> Object[15];
    Class[] petTypes = {
      <font color=#009900>// Class literals:</font>
      Pet.<font color=#0000ff>class</font>,
      Dog.<font color=#0000ff>class</font>,
      Pug.<font color=#0000ff>class</font>,
      Cat.<font color=#0000ff>class</font>,
      Rodent.<font color=#0000ff>class</font>,
      Gerbil.<font color=#0000ff>class</font>,
      Hamster.<font color=#0000ff>class</font>,
    };
    <font color=#0000ff>try</font> {
      <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++) {
        <font color=#009900>// Offset by one to eliminate Pet.class:</font>
        <font color=#0000ff>int</font> rnd = 1 + rand.nextInt(petTypes.length - 1);
        pets[i] = petTypes[rnd].newInstance();
      }
    } <font color=#0000ff>catch</font>(InstantiationException e) {
      System.out.println(<font color=#004488>"Cannot instantiate"</font>);
      System.exit(1);
    } <font color=#0000ff>catch</font>(IllegalAccessException e) {
      System.out.println(<font color=#004488>"Cannot access"</font>);
      System.exit(1);
    }
    AssociativeArray map =
      <font color=#0000ff>new</font> AssociativeArray(petTypes.length);
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; petTypes.length; i++)
      map.put(petTypes[i].toString(), <font color=#0000ff>new</font> Counter());
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++) {
      Object o = pets[i];
      <font color=#009900>// Using Class.isInstance() to eliminate</font>
      <font color=#009900>// individual instanceof expressions:</font>
      <font color=#0000ff>for</font>(<font color=#0000ff>int</font> j = 0; j &lt; petTypes.length; ++j)
        <font color=#0000ff>if</font>(petTypes[j].isInstance(o))
          ((Counter)map.get(petTypes[j].toString())).i++;
    }
    <font color=#009900>// List each individual pet:</font>
    <font color=#0000ff>for</font>(<font color=#0000ff>int</font> i = 0; i &lt; pets.length; i++)
      System.out.println(pets[i].getClass());
    <font color=#009900>// Show the counts:</font>
    System.out.println(map);
    monitor.expect(<font color=#0000ff>new</font> Object[] {
      <font color=#0000ff>new</font> TestExpression(<font color=#004488>"%% class c10\\."</font> +

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -