I think it does what it asks for. Can someone point what the problem is?
package com.codegym.task.task35.task3507;
import java.io.File;
import java.lang.reflect.Constructor;
import java.nio.file.Files;
import java.util.*;
/*
What is ClassLoader?
*/
public class Solution {
private static List<String> result = new ArrayList<>();
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException {
Set<? extends Animal> allAnimals = getAllAnimals(Solution.class.getProtectionDomain().getCodeSource().getLocation().getPath() + Solution.class.getPackage().getName().replaceAll("[.]", "/") + "/data");
System.out.println(allAnimals);
}
public static Set<? extends Animal> getAllAnimals(String pathToAnimals) throws ClassNotFoundException, IllegalAccessException, InstantiationException {
Set<Animal> set = new HashSet<>();
final File folder = new File(pathToAnimals);
search(".class", folder, result);
ClassLoader classLoader = new ClassLoader() {
@Override
public Class<?> findClass(String name) throws ClassNotFoundException {
try {
File file = new File(name);
byte [] byteArray = Files.readAllBytes(new File(name).toPath());
String s = Solution.class.getPackage().getName()+".data."+file.getName().substring(0, file.getName().length()-6);
return defineClass(s, byteArray, 0, byteArray.length);
} catch (Exception e) {
e.printStackTrace();
}
return super.findClass(name);
}
};
for(String s : result){
Class<?> clazz = classLoader.loadClass(s);
Constructor<?> [] constructors = clazz.getConstructors();
boolean hasDefaultConstructor = false;
boolean hasAnimalInterface = false;
for(Constructor<?> constructor : constructors){
if(constructor.getParameterCount()==0) {
hasDefaultConstructor = true;
break;
}
}
Class<?> [] interfaces = clazz.getInterfaces();
for(Class<?> interfase : interfaces){
if(interfase.equals(Animal.class)) {
hasAnimalInterface = true;
break;
}
}
if(hasAnimalInterface && hasDefaultConstructor) set.add((Animal)clazz.newInstance());
}
return set;
}
public static void search(final String pattern, final File folder, List<String> result) {
for (final File f : folder.listFiles()) {
if (f.isDirectory()) {
search(pattern, f, result);
}
if (f.isFile()) {
if (f.getName().endsWith(pattern)) {
result.add(f.getAbsolutePath());
}
}
}
}
}