Java がリフレクションを使用して、指定されたアノテーションを使用してクラスを検索する方法の詳細な説明

黄舟
リリース: 2017-09-30 10:24:16
オリジナル
1907 人が閲覧しました

この記事では、Java が指定されたアノテーションを使用するクラスを見つけるためにどのようにリフレクションを使用するかについて、主に関連情報を紹介します。この記事は、すべての学習や仕事に役立つ特定の学習価値があります。以下のエディタを使用して。

はじめに

最近少し時間ができたので、春と同じアノテーションを書きたいと思います。それでは、私が書いたアノテーションを使用するクラスを見つけたいと思います

。ステートメント、次のコードは、基本的にオンラインで見つかったブログからコンパイルされました。


@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Controller {

}
ログイン後にコピー

アノテーションを使用する

@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RequestMapping {

 String value();

}
ログイン後にコピー


パッケージの下のすべてのクラスをスキャンする


次のコードは

rrから取得されますreee パッケージ名を渡すと、以下のすべてのクラスを自動的にスキャンして


アノテーション付きクラスを見つけます

@Controller
public class IndexController {

 @RequestMapping("/")
 public void index() {
 System.out.println("index method")
 }

 @RequestMapping("/about")
 public void about(String args) {
 System.out.println("about method")
 }

}
ログイン後にコピー
RequestMapping アノテーションが付いているメソッドを見つけて、挿入されたパラメータを見つけます

/**
 * 从包package中获取所有的Class
 *
 * @param packageName
 * @return
 */
public static List<Class<?>> getClasses(String packageName) {

 // 第一个class类的集合
 List<Class<?>> classes = new ArrayList<Class<?>>();
 // 是否循环迭代
 boolean recursive = true;
 // 获取包的名字 并进行替换
 String packageDirName = packageName.replace(&#39;.&#39;, &#39;/&#39;);
 // 定义一个枚举的集合 并进行循环来处理这个目录下的things
 Enumeration<URL> dirs;
 try {
 dirs = Thread.currentThread().getContextClassLoader().getResources(packageDirName);
 // 循环迭代下去
 while (dirs.hasMoreElements()) {
  // 获取下一个元素
  URL url = dirs.nextElement();
  // 得到协议的名称
  String protocol = url.getProtocol();
  // 如果是以文件的形式保存在服务器上
  if ("file".equals(protocol)) {
  // 获取包的物理路径
  String filePath = URLDecoder.decode(url.getFile(), "UTF-8");
  // 以文件的方式扫描整个包下的文件 并添加到集合中
  findAndAddClassesInPackageByFile(packageName, filePath, recursive, classes);
  } else if ("jar".equals(protocol)) {
  // 如果是jar包文件
  // 定义一个JarFile
  JarFile jar;
  try {
   // 获取jar
   jar = ((JarURLConnection) url.openConnection()).getJarFile();
   // 从此jar包 得到一个枚举类
   Enumeration<JarEntry> entries = jar.entries();
   // 同样的进行循环迭代
   while (entries.hasMoreElements()) {
   // 获取jar里的一个实体 可以是目录 和一些jar包里的其他文件 如META-INF等文件
   JarEntry entry = entries.nextElement();
   String name = entry.getName();
   // 如果是以/开头的
   if (name.charAt(0) == &#39;/&#39;) {
    // 获取后面的字符串
    name = name.substring(1);
   }
   // 如果前半部分和定义的包名相同
   if (name.startsWith(packageDirName)) {
    int idx = name.lastIndexOf(&#39;/&#39;);
    // 如果以"/"结尾 是一个包
    if (idx != -1) {
    // 获取包名 把"/"替换成"."
    packageName = name.substring(0, idx).replace(&#39;/&#39;, &#39;.&#39;);
    }
    // 如果可以迭代下去 并且是一个包
    if ((idx != -1) || recursive) {
    // 如果是一个.class文件 而且不是目录
    if (name.endsWith(".class") && !entry.isDirectory()) {
     // 去掉后面的".class" 获取真正的类名
     String className = name.substring(packageName.length() + 1, name.length() - 6);
     try {
     // 添加到classes
     classes.add(Class.forName(packageName + &#39;.&#39; + className));
     } catch (ClassNotFoundException e) {
     e.printStackTrace();
     }
    }
    }
   }
   }
  } catch (IOException e) {
   e.printStackTrace();
  }
  }
 }
 } catch (IOException e) {
 e.printStackTrace();
 }

 return classes;
}
ログイン後にコピー

このようにして、純粋なサーブレットで書かれた Java プロジェクトでは、独自のアノテーション マッピング ルーティングを行うことができ、非常に便利です


概要

以上がJava がリフレクションを使用して、指定されたアノテーションを使用してクラスを検索する方法の詳細な説明の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

関連ラベル:
ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート