友情提示:如果本网页打开太慢或显示不完整,请尝试鼠标右键“刷新”本网页!阅读过程发现任何错误请告诉我们,谢谢!! 报告错误
狗狗书籍 返回本书目录 我的书架 我的书签 TXT全本下载 进入书吧 加入书签

Java编程思想第4版[中文版](PDF格式)-第154章

按键盘上方向键 ← 或 → 可快速上下翻页,按键盘上的 Enter 键可回到本书目录页,按键盘上方向键 ↑ 可回到本页顶部!
————未阅读完?加入书签已便下次继续阅读!




11。3。1 一个类方法提取器  



很少需要直接使用反射工具;之所以在语言中提供它们,仅仅是为了支持其他Java 特性,比如对象序列化 

 (第10章介绍)、Java Beans 以及RMI (本章后面介绍)。但是,我们许多时候仍然需要动态提取与一个类 

有关的资料。其中特别有用的工具便是一个类方法提取器。正如前面指出的那样,若检视类定义源码或者联 

机文档,只能看到在那个类定义中被定义或覆盖的方法,基础类那里还有大量资料拿不到。幸运的是,“反 

射”做到了这一点,可用它写一个简单的工具,令其自动展示整个接口。下面便是具体的程序:  

  

//: ShowMethods。java  

// Using Java 1。1 reflection to show all the   

// methods of a class; even if the methods are   

// defined in the base class。  

import java。lang。reflect。*;  

  

public class ShowMethods {  

  static final String usage =  

    〃usage: n〃 +  

    〃ShowMethods qualified。class。namen〃 +  

    〃To show all methods in class or: n〃 +  

    〃ShowMethods qualified。class。name wordn〃 +  

    〃To search for methods involving 'word'〃;  

  public static void main(String'' args) {  

    if(args。length 《 1) {  

      System。out。println(usage);  

      System。exit(0);  

    }  

    try {  



                                                                              344 


…………………………………………………………Page 346……………………………………………………………

      Class c = Class。forName(args'0');  

      Method'' m = c。getMethods();  

      Constructor'' ctor = c。getConstructors();  

      if(args。length == 1) {  

        for (int i = 0; i 《 m。length; i++)  

          System。out。println(m'i'。toString());  

        for (int i = 0; i 《 ctor。length; i++)  

          System。out。println(ctor'i'。toString());  

      }   

      else {  

        for (int i = 0; i 《 m。length; i++)  

          if(m'i'。toString()  

             。indexOf(args'1')!= …1)  

            System。out。println(m'i'。toString());  

        for (int i = 0; i 《 ctor。length; i++)  

          if(ctor'i'。toString()  

             。indexOf(args'1')!= …1)  

          System。out。println(ctor'i'。toString());  

      }  

    } catch (ClassNotFoundException e) {  

      System。out。println(〃No such class: 〃 + e);  

    }  

  }  

} ///:~  

  

Class 方法getMethods()和 getConstructors()可以分别返回Method 和Constructor 的一个数组。每个类都 

提供了进一步的方法,可解析出它们所代表的方法的名字、参数以及返回值。但也可以象这样一样只使用 

toString(),生成一个含有完整方法签名的字串。代码剩余的部分只是用于提取命令行信息,判断特定的签 

名是否与我们的目标字串相符(使用 indexOf()),并打印出结果。  

这里便用到了“反射”技术,因为由Class。forName()产生的结果不能在编译期间获知,所以所有方法签名 

信息都会在运行期间提取。若研究一下联机文档中关于“反射”(Reflection)的那部分文字,就会发现它 

已提供了足够多的支持,可对一个编译期完全未知的对象进行实际的设置以及发出方法调用。同样地,这也 

属于几乎完全不用我们操心的一个步骤——Java 自己会利用这种支持,所以程序设计环境能够控制Java  

Beans——但它无论如何都是非常有趣的。  

一个有趣的试验是运行 java ShowMehods ShowMethods。这样做可得到一个列表,其中包括一个public 默认 

构建器,尽管我们在代码中看见并没有定义一个构建器。我们看到的是由编译器自动合成的那一个构建器。 

如果随之将 ShowMethods 设为一个非 public 类(即换成“友好”类),合成的默认构建器便不会在输出结果 

中出现。合成的默认构建器会自动获得与类一样的访问权限。  

ShowMethods 的输出仍然有些“不爽”。例如,下面是通过调用 java ShowMethods java。lang。String得到 

的输出结果的一部分:  

  

public boolean   

  java。lang。String。startsWith(java。lang。String;int)  

public boolean   

  java。lang。String。startsWith(java。lang。String)  

public boolean  

  java。lang。String。endsWith(java。lang。String)  

  

若能去掉象 java。lang 这样的限定词,结果显然会更令人满意。有鉴于此,可引入上一章介绍的 

StreamTokenizer 类,解决这个问题:  

  

//: ShowMethodsClean。java  



                                                                                          345 


…………………………………………………………Page 347……………………………………………………………

// ShowMethods with the qualifiers stripped  

// to make the results easier to read  

import java。lang。reflect。*;  

import java。io。*;  

  

public class ShowMethodsClean {  

  static final String usage =  

    〃usage: n〃 +  

    〃ShowMethodsClean qualified。class。namen〃 +  

    〃To show all methods in class or: n〃 +  

    〃ShowMethodsClean qualif。class。name wordn〃 +  

    〃To search for methods involving 'word'〃;  

  public static void main(String'' args) {  

    if(args。length 《 1) {  

      System。out。println(usage);  

      System。exit(0);  

    }  

    try {  

      Class c = Class。forName(args'0');  

      Method'' m = c。getMethods();  

      Constructor'' ctor = c。getConstructors();  

      // Convert to an array of cleaned Strings:  

      String'' n =   

        new String'm。length + ctor。length';  

      for(int i = 0; i 《 m。length; i++) {  

        String s = m'i'。toString();  

        n'i' = StripQualifiers。strip(s);  

      }  

      for(int i = 0; i 《 ctor。length; i++) {  

        String s = ctor'i'。toString();  

        n'i + m。length' =   

          StripQualifiers。strip(s);  

      }  

      if(args。length == 1)  

        for (int i = 0; i 《 n。length; i++)  

          System。out。println(n'i');  

      else  

        for (int i = 0; i 《 n。length; i++)  

          if(n'i'。indexOf(args'1')!= …1)  

            System。out。println(n'i');  

    } catch (ClassNotFoundException e) {  

      System。out。println(〃No such class: 〃 + e);  

    }  

  }  

}  

  

class StripQualifiers {  

  private StreamTokenizer st;  

  public StripQualifiers(String qualified) {  

      st = new StreamTokenizer(  

        new StringReader(qualified));  

      st。ordinaryChar(' '); // Keep the spaces  



                                                                                             346 


…………………………………………………………Page 348……………………………………………………………

  }  

  public String getNext() {  

    String s = null;  

    try {  

      if(s
返回目录 上一页 下一页 回到顶部 0 0
未阅读完?加入书签已便下次继续阅读!
温馨提示: 温看小说的同时发表评论,说出自己的看法和其它小伙伴们分享也不错哦!发表书评还可以获得积分和经验奖励,认真写原创书评 被采纳为精评可以获得大量金币、积分和经验奖励哦!