我已經使用JavaCompiler
來編譯我在運行中生成的類。編譯任務成功。然後我嘗試使用Class.forName("MyClass")
加載編譯的類;並且它以ClassNotFoundException失敗。這樣做有沒有已知的問題?未找到JavaCompiler編譯類
package com.amir.method;
import java.io.*;
import java.lang.reflect.Method;
import java.net.URI;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Set;
import javax.tools.*;
public class MethodGenerator {
private final static MethodGenerator INSTANCE = new MethodGenerator();
private MethodGenerator() {
}
public static MethodGenerator get() {
return INSTANCE;
}
public static void main(String[] args) {
final Class<?> clz = MethodGenerator.get().compile("Foo", "doIt"); //<- args ignored for now
}
public Class compile(final String className,
final String methodName) {
try {
return doCompile(className, methodName);
} catch(final Exception e) {
throw new RuntimeException(this.toString(), e);
}
}
private Class doCompile(final String className,
final String methodName) throws IOException, ClassNotFoundException {
JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
DiagnosticCollector<JavaFileObject> diagnostics = new DiagnosticCollector<JavaFileObject>();
StringWriter writer = new StringWriter();
PrintWriter out = new PrintWriter(writer);
out.println("public class HelloWorld {");
out.println(" public static void main(String args[]) {");
out.println(" System.out.println(\"This is in another java file\");");
out.println(" }");
out.println("}");
out.close();
final JavaFileObject file = new JavaSourceFromString("HelloWorld", writer.toString());
final Iterable<? extends JavaFileObject> compilationUnits = Arrays.asList(file);
final String classPath = System.getProperty("java.class.path") + File.pathSeparator;
final String bootClassPath = System.getProperty("sun.boot.class.path") + File.pathSeparator;
final List<String> options = new ArrayList<String>();
options.add("-classpath");
final StringBuilder builder = new StringBuilder();
builder.append(classPath);
builder.append(bootClassPath);
final URLClassLoader urlClassLoader = (URLClassLoader) ClassLoaderResolver.getClassLoader();
for (final URL url : urlClassLoader.getURLs()) {
builder.append(url.getFile()).append(File.pathSeparator);
}
final int lastIndexOfColon = builder.lastIndexOf(File.pathSeparator);
builder.replace(lastIndexOfColon, lastIndexOfColon + 1, "");
options.add(builder.toString());
final JavaCompiler.CompilationTask task = compiler.getTask(null, null, diagnostics, options, null, compilationUnits);
boolean success = task.call();
if(success) {
final Class<?> cls = Class.forName("HelloWorld", true, urlClassLoader);
return cls;
}
return null;
}
class JavaSourceFromString extends SimpleJavaFileObject {
final String code;
JavaSourceFromString(String name, String code) {
super(URI.create("string:///" + name.replace('.', '/') + Kind.SOURCE.extension),Kind.SOURCE);
this.code = code;
}
@Override
public CharSequence getCharContent(boolean ignoreEncodingErrors) {
return code;
}
}
}
您是否檢查過您的清單,如果導出/導入該類?你如何建立你的項目。嘗試重新生成清單文件。 – StackFlowed 2014-11-06 17:56:56
清單?我正在編譯一個課程。我不確定我明白清單文件會做什麼? – 2014-11-06 17:58:37
編譯該類不會自動將其添加到類加載器。你需要自己做。 – Paul 2014-11-06 18:02:42