现在听起来您想从规范名称中获取完全限定名称 (FQN)。由于这与使用简单名称不同,我将添加第二个答案。
如果会导致规范名称冲突,Sun javac 命令将不会编译类。但是,通过单独编译,您仍然可以获得具有相同规范名称的两个不同类。
一个例子:
文件 src1\com\stack\Test.java
package com.stack;
public class Test {
public static class Example {
public static class Cow {
public static class Hoof {
}
}
}
public static void main(String[] args) throws Exception {
Class<?> cl1 = Class.forName("com.stack.Test$Example$Cow$Hoof");
Class<?> cl2 = Class.forName("com.stack.Test.Example.Cow.Hoof");
System.out.println(cl1.getName());
System.out.println(cl1.getSimpleName());
System.out.println(cl1.getCanonicalName());
System.out.println();
System.out.println(cl2.getName());
System.out.println(cl2.getSimpleName());
System.out.println(cl2.getCanonicalName());
}
}
文件 src2\com\stack\Test\Example\Cow\Hoof.java
package com.stack.Test.Example.Cow;
public class Hoof { }
然后编译并执行:
set CLASSPATH=
mkdir bin1 bin2
javac -d bin1 -sourcepath src1 src1\com\stack\Test.java
javac -d bin2 -sourcepath src2 src2\com\stack\Test\Example\Cow\Hoof.java
set CLASSPATH=bin1;bin2
java com.stack.Test
产生输出:
com.stack.Test$Example$Cow$Hoof
Hoof
com.stack.Test.Example.Cow.Hoof
com.stack.Test.Example.Cow.Hoof
Hoof
com.stack.Test.Example.Cow.Hoof
因此,两个类具有相同的规范名称但不同的 FQN。即使两个类具有相同的 FQN 和相同的规范名称,如果它们通过不同的类加载器加载,它们仍然可能不同。
为了解决您的问题,我看到了您可以采取的几种前进方式。
首先,您可以指定您匹配具有最少嵌套量的类,因此 FQN 中的“$”数量最少。更新事实证明,Sun javac 与此完全相反,并且匹配嵌套最多的类。
其次,您可以测试所有可能的 FQN,如果有多个则抛出异常。
第三,接受唯一的唯一映射是与 FQN,然后仅在指定的类加载器中,并适当地重新处理您的应用程序。我发现使用线程上下文类加载器作为默认类加载器很方便。