我想做这样的事情:
List<Animal> animals = new ArrayList<Animal>();
for( Class c: list_of_all_classes_available_to_my_app() )
if (c is Animal)
animals.add( new c() );
So, I want to look at all of the classes in my application's universe, and when I find one that descends from Animal, I want to create a new object of that type and add it to the list. This allows me to add functionality without having to update a list of things. I can avoid the following:
List<Animal> animals = new ArrayList<Animal>();
animals.add( new Dog() );
animals.add( new Cat() );
animals.add( new Donkey() );
...
With the above approach, I can simply create a new class that extends Animal and it'll get picked up automatically.
UPDATE: 10/16/2008 9:00 a.m. Pacific Standard Time:
This question has generated a lot of great responses -- thank you. From the responses and my research, I've found that what I really want to do is just not possible under Java. There are approaches, such as ddimitrov's ServiceLoader mechanism that can work -- but they are very heavy for what I want, and I believe I simply move the problem from Java code to an external configuration file. Update 5/10/19 (11 years later!) There are now several libraries that can help with this according to @IvanNik's 回答 org.reflections 看起来不错。还 ClassGraph from @Luke Hutchison's 回答 looks interesting. There are several more possibilities in the answers as well.
Another way to state what I want: a static function in my Animal class finds and instantiates all classes that inherit from Animal -- without any further configuration/coding. If I have to configure, I might as well just instantiate them in the Animal class anyway. I understand that because a Java program is just a loose federation of .class files that that's just the way it is.
Interestingly, it seems this is fairly trivial 在c#中。
我用 org.reflections:
Reflections reflections = new Reflections("com.mycompany");
Set<Class<? extends MyInterface>> classes = reflections.getSubTypesOf(MyInterface.class);
另一个例子:
public static void main(String[] args) throws IllegalAccessException, InstantiationException {
Reflections reflections = new Reflections("java.util");
Set<Class<? extends List>> classes = reflections.getSubTypesOf(java.util.List.class);
for (Class<? extends List> aClass : classes) {
System.out.println(aClass.getName());
if(aClass == ArrayList.class) {
List list = aClass.newInstance();
list.add("test");
System.out.println(list.getClass().getName() + ": " + list.size());
}
}
}
Applies To The Information provided in this article applies to the following technologies: Windows Server 2003 family OS, IIS 6.0, .Net Framework 2.0 & Asp.Net 2.0 Introduction Web application sec...
打开软件出现以上错误。 解决方法: 打开STM32cubeMX.exe所在的安装文件夹, 按住Shift键,在文件夹空白处点击鼠标右键,点击“在此处打开PowerShell窗口”, 然后输入 java -jar 要打开的文件名(包括后缀名) ,然后回车即可打开文件,该方法同样适用打开.jar和一些其他的文件。...
系统已经安装过了java1.8(解压缩版的),已经安装了 jdk ,并且设置好了 java 环境变量,CMD 运行 java 或 javac 都正常,其他依赖 jdk 的应用程序都能正常运行,安装完FreeMind提示需要java1.5.0环境 解决方法如下: 1:点击上图中提示的确定按钮,浏览器自动跳转到下图,接着根据提示安装java环境; 2.安装成功后,双击桌面FreeMind图标就能成功运...
运行 jadx-gui-0.9.0.exe 应用程序时报: This application requires a Java Runtime Environment 1.8.0 (64-bit) 不同的 jadx-gui.exe 提示的信息可能不同,低版本的可能是: This application requires a Java Runtime Environment 1.7.0 找不到jre环...
Eclipse编辑器Gradle(STS)编译代码,报错的问题 使用Gradle(STS)build报错:java.lang.RuntimeException: Cannot find System Java Compiler. Ensure that you have install a JDK not a JRE 首先排查eclipse是否已经导入相应的jre 查看方法:Window----&...
eclipse在启动的时候需要设置默认的jdk地址,即javaw.exe文件的地址,该地址和eclipse的编译jdk路径需要一致,如果没有加上的话需要加上(特别是在用构建工具如gradle的时候,没用过maven和ant,不知道是不是也受这个影响) 解决的主要步骤:编辑eclipse目录下的eclipse.ini,该文件是eclipse的初始化文件,需要在文件开头加上 -vm C:\Progra...
导入github上的项目,有时候,就会报如下的错误 Error:Execution failed for task ':app:compileDebugJava'. > Cannot find System Java Compiler. Ensure that you have installed a JDK (not just a JRE) and configured your JAVA...
背景: redis字典(hash表)当数据越来越多的时候,就会发生扩容,也就是rehash 对比:java中的hashmap,当数据数量达到阈值的时候(0.75),就会发生rehash,hash表长度变为原来的二倍,将原hash表数据全部重新计算hash地址,重新分配位置,达到rehash目的 redis中的hash表采用的是渐进式hash的方式: 1、redis字典(hash表)底层有...
2019独角兽企业重金招聘Python工程师标准>>> 我们平时按下键盘上的‘回车键’,就能实现回车换行【我们在屏幕上所看到的就是光标移到了下一行的开头位置!!ps:不讨论软件实现的特殊功能,如word里的回车智能缩进】。因此对这个按键更准确说应该叫做‘回车换行键’ 就且将这种将光标移到下行开...
首先,在Windows操作系统下安装python,完成python环境的搭建。(我看有的博客需要配置环境变量,其实不必要,因为我们在安装的时候只要勾选如下图所示即可避免不必要的麻烦) 第二步,使用快捷键windows+R或者点击如下图所示,之后点击运行 在其中输入cmd即可进入dos命令。 第三步,输入以下命令 就会自动安装,等待安装完成即可。 第四步,检测django是否安装成功,如果出现如下图...
I have a dataframe and i want to calculate the sum of variables present in a vector in every row and make the sum in other variable after i want the name of new variable created to be from the name of...
I have a very rough project that done partially in zend framework (not ZF2). The 'application', 'library' and 'public' folders are on the same root. Now i need to create a library 'Anil' in the 'libra...
I want to hide some of the categories from magento home page. I have created some categories like New Arrivals, Special Offer Which I would like to show in some different way may be in left panel or r...
I am writing to an internal file in Android Studio The code lets me write lines of data split with commas. I am able to then go to another activity and read it all out at once. However I want to be ab...
I'm new to Ruby On Rails, I used the acts_as_votable gem to create Like and Unlike Buttons to make Users like and unlike Posts but I can't make them change from Like to Unlike (and viceversa) and upda...