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

📄 tij0150.html

📁 学习java的经典书籍
💻 HTML
📖 第 1 页 / 共 4 页
字号:
<DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">One
of the most critical parts of the Bean scheme occurs when you drag a Bean off a
palette and plop it down on a form. The application builder tool must be able
to create the Bean (which it can do if there&#8217;s a default constructor) and
then, without access to the Bean&#8217;s source code, extract all the necessary
information to create the property sheet and event handlers.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Part
of the solution is already evident from the end of Chapter 11: Java 1.1<A NAME="Index2204"></A>
<A NAME="Index2205"></A><A NAME="Index2206"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><I>reflection</I></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
allows all the methods of an anonymous class to be discovered. This is perfect
for solving the Bean problem without requiring you to use any extra language
keywords like those required in other visual programming languages. In fact,
one of the prime reasons that reflection was added to Java 1.1 was to support
Beans (although reflection also supports object serialization and remote method
invocation). So you might expect that the creator of the application builder
tool would have to reflect each Bean and hunt through its methods to find the
properties and events for that Bean.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">This
is certainly possible, but the Java designers wanted to provide a standard
interface for everyone to use, not only to make Beans simpler to use but also
to provide a standard gateway to the creation of more complex Beans. This
interface is the <A NAME="Index2207"></A><A NAME="Index2208"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Introspector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class, and the most important method in this class is the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>static
<A NAME="Index2209"></A><A NAME="Index2210"></A>getBeanInfo(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
You pass a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Class</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
handle to this method and it fully interrogates that class and returns a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanInfo</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object that you can then dissect to find properties, methods, and events.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">Usually
you won&#8217;t care about any of this &#8211; you&#8217;ll probably get most
of your Beans off the shelf from vendors, and you don&#8217;t need to know all
the magic that&#8217;s going on underneath. You&#8217;ll simply drag your Beans
onto your form, then configure their properties and write handlers for the
events you&#8217;re interested in. However, it&#8217;s an interesting and
educational exercise to use the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Introspector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
to display information about a Bean, so here&#8217;s a tool that does it
(you&#8217;ll find it in the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>frogbean</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
subdirectory):
</FONT><P></DIV>

<font color="#990000"><PRE><font color="#009900">//: BeanDumper.java</font>
<font color="#009900">// A method to introspect a Bean</font>
<font color="#0000ff">import</font> java.beans.*;
<font color="#0000ff">import</font> java.lang.reflect.*;

<font color="#0000ff">public</font> <font color="#0000ff">class</font> BeanDumper {
  <font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> dump(Class bean){
    BeanInfo bi = <font color="#0000ff">null</font>;
    <font color="#0000ff">try</font> {
      bi = Introspector.getBeanInfo(
        bean, java.lang.Object.<font color="#0000ff">class</font>);
    } <font color="#0000ff">catch</font>(IntrospectionException ex) {
      System.out.println("Couldn't introspect " +
        bean.getName());
      System.exit(1);
    }
    PropertyDescriptor[] properties = 
      bi.getPropertyDescriptors();
    <font color="#0000ff">for</font>(<font color="#0000ff">int</font> i = 0; i &lt; properties.length; i++) {
      Class p = properties[i].getPropertyType();
      System.out.println(
        "Property type:\n  " + p.getName());
      System.out.println(
        "Property name:\n  " + 
        properties[i].getName());
      Method readMethod = 
        properties[i].getReadMethod();
      <font color="#0000ff">if</font>(readMethod != <font color="#0000ff">null</font>)
        System.out.println(
          "Read method:\n  " + 
          readMethod.toString());
      Method writeMethod = 
        properties[i].getWriteMethod();
      <font color="#0000ff">if</font>(writeMethod != <font color="#0000ff">null</font>)
        System.out.println(
          "Write method:\n  " +
          writeMethod.toString());
      System.out.println("====================");
    }
    System.out.println("Public methods:");
    MethodDescriptor[] methods =
      bi.getMethodDescriptors();
    <font color="#0000ff">for</font>(<font color="#0000ff">int</font> i = 0; i &lt; methods.length; i++)
      System.out.println(
        methods[i].getMethod().toString());
    System.out.println("======================");
    System.out.println("Event support:");
    EventSetDescriptor[] events = 
      bi.getEventSetDescriptors();
    <font color="#0000ff">for</font>(<font color="#0000ff">int</font> i = 0; i &lt; events.length; i++) {
      System.out.println("Listener type:\n  " +
        events[i].getListenerType().getName());
      Method[] lm = 
        events[i].getListenerMethods();
      <font color="#0000ff">for</font>(<font color="#0000ff">int</font> j = 0; j &lt; lm.length; j++)
        System.out.println(
          "Listener method:\n  " +
          lm[j].getName());
      MethodDescriptor[] lmd = 
        events[i].getListenerMethodDescriptors();
      <font color="#0000ff">for</font>(<font color="#0000ff">int</font> j = 0; j &lt; lmd.length; j++)
        System.out.println(
          "Method descriptor:\n  " +
          lmd[j].getMethod().toString());
      Method addListener = 
        events[i].getAddListenerMethod();
      System.out.println(
          "Add Listener Method:\n  " +
        addListener.toString());
      Method removeListener =
        events[i].getRemoveListenerMethod();
      System.out.println(
        "Remove Listener Method:\n  " +
        removeListener.toString());
      System.out.println("====================");
    }
  }
  <font color="#009900">// Dump the class of your choice:</font>
  <font color="#0000ff">public</font> <font color="#0000ff">static</font> <font color="#0000ff">void</font> main(String[] args) {
    <font color="#0000ff">if</font>(args.length &lt; 1) {
      System.err.println("usage: \n" +
        "BeanDumper fully.qualified.<font color="#0000ff">class</font>");
      System.exit(0);
    }
    Class c = <font color="#0000ff">null</font>;
    <font color="#0000ff">try</font> {
      c = Class.forName(args[0]);
    } <font color="#0000ff">catch</font>(ClassNotFoundException ex) {
      System.err.println(
        "Couldn't find " + args[0]);
      System.exit(0);
    }
    dump(c);
  }
} <font color="#009900">///:~ </PRE></font></font><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanDumper.dump(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
is the method that does all the work. First it tries to create a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanInfo</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object, and if successful calls the methods of 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanInfo</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
that produce information about properties, methods, and events. In 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Introspector.getBeanInfo(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
you&#8217;ll see there is a second argument. This tells the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Introspector</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
where to stop in the inheritance hierarchy. Here, it stops before it parses all
the methods from 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Object</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
since we&#8217;re not interested in seeing those.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">For
properties, <A NAME="Index2211"></A><A NAME="Index2212"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getPropertyDescriptors(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
returns an array of <A NAME="Index2213"></A><A NAME="Index2214"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>PropertyDescriptor</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">s.
For each 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>PropertyDescriptor</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
you can call <A NAME="Index2215"></A><A NAME="Index2216"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getPropertyType(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
to find the class of object that is passed in and out via the property methods.
Then, for each property you can get its pseudonym (extracted from the method
names) with <A NAME="Index2217"></A><A NAME="Index2218"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getName(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">,
the method for reading with <A NAME="Index2219"></A><A NAME="Index2220"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getReadMethod(&#160;),</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
and the method for writing with <A NAME="Index2221"></A><A NAME="Index2222"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getWriteMethod(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">.
These last two methods return a 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Method</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object that can actually be used to invoke the corresponding method on the
object (this is part of reflection).
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">For
the public methods (including the property methods), <A NAME="Index2223"></A><A NAME="Index2224"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getMethodDescriptors(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
returns an array of <A NAME="Index2225"></A><A NAME="Index2226"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>MethodDescriptor</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">s.
For each one you can get the associated <A NAME="Index2227"></A><A NAME="Index2228"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Method</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
object and print out its name.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">For
the events, <A NAME="Index2229"></A><A NAME="Index2230"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>getEventSetDescriptors(&#160;)</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
returns an array of (what else?) <A NAME="Index2231"></A><A NAME="Index2232"></A></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>EventSetDescriptor</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">s.
Each of these can be queried to find out the class of the listener, the methods
of that listener class, and the add- and remove-listener methods. The 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanDumper
</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">program
prints out all of this information.
</FONT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">If
you invoke 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>BeanDumper</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
on the 
</FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black"><B>Frog</B></FONT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">
class like this:
</FONT><P></DIV><DIV ALIGN=LEFT><TT><FONT FACE="Courier New" SIZE=3 COLOR="Black">java
BeanDumper frogbean.Frog
</FONT></TT><P></DIV><DIV ALIGN=LEFT><P></DIV><DIV ALIGN=LEFT><FONT FACE="Carmina Md BT" SIZE=3 COLOR="Black">the
output, after removing extra details that are unnecessary here, is:
</FONT><P></DIV>

<font color="#990000"><PRE><font color="#0000ff">class</font> name: Frog
Property type:
  Color
Property name:
  color
Read method:
  <font color="#0000ff">public</font> Color getColor()
Write method:
  <font color="#0000ff">public</font> <font color="#0000ff">void</font> setColor(Color)
====================
Property type:
  Spots
Property name:
  spots
Read method:
  <font color="#0000ff">public</font> Spots getSpots()
Write method:
  <font color="#0000ff">public</font> <font color="#0000ff">void</font> setSpots(Spots)
====================
Property type:
  <font color="#0000ff">boolean</font>
Property name:
  jumper
Read method:
  <font color="#0000ff">public</font> <font color="#0000ff">boolean</font> isJumper()
Write method:
  <font color="#0000ff">public</font> <font color="#0000ff">void</font> setJumper(<font color="#0000ff">boolean</font>)
====================
Property type:
  <font color="#0000ff">int</font>
Property name:
  jumps
Read method:
  <font color="#0000ff">public</font> <font color="#0000ff">int</font> getJumps()
Write method:
  <font color="#0000ff">public</font> <font color="#0000ff">void</font> setJumps(<font color="#0000ff">int</font>)
====================
Public methods:
<font color="#0000ff">public</font> <font color="#0000ff">void</font> setJumps(<font color="#0000ff">int</font>)

⌨️ 快捷键说明

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