Java 将字符串动态生成字节码的实现方法

时间:2021-05-20

可以生成可执行的class文件

直接上能执行代码:
复制代码 代码如下:
public class Test {

/**
* @param args
*/
@SuppressWarnings("static-access")
public static void main(String[] args) {
try {
new Test().calculate("234 - ( 1 + 45 * 4 ) / 5");
} catch (Exception e) {
e.printStackTrace();
}
}

private static double calculate(String expr) throws Exception {
String className = "CalculatorMain";
String methodName = "calculate";
String source = "class " + className
+ " { public static void main(String[] args){System.out.println(calculate());} public static double " + methodName + "() { return "
+ expr + "; } }";
JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
StandardJavaFileManager fileManager = compiler.getStandardFileManager(
null, null, null);
StringSourceJavaObject sourceObject = new Test.StringSourceJavaObject(
"Main", source);
Iterable<? extends JavaFileObject> fileObjects = Arrays
.asList(sourceObject);
CompilationTask task = compiler.getTask(null, fileManager, null, null,
null, fileObjects);

boolean result = task.call();
if (result) {
ClassLoader loader = Thread.currentThread().getClass()
.getClassLoader();
try {
Class<?> clazz = loader.loadClass(className);
Method method = clazz.getMethod(methodName, new Class<?>[] {});
Object value = method.invoke(null, new Object[] {});
return (Double)value;
} catch (Exception e) {
// throw new CalculationException("内部错误。");
}
} else {
// / new CalculationException("错误的表达式。");
}
return 0;
}

static class StringSourceJavaObject extends SimpleJavaFileObject {

private String content = null;

public StringSourceJavaObject(String name, String content)
throws URISyntaxException {
super(URI.create("string:///" + name.replace('.', '/')
+ Kind.SOURCE.extension), Kind.SOURCE);
this.content = content;
}

public CharSequence getCharContent(boolean ignoreEncodingErrors)
throws IOException {
return content;
}
}

}

声明:本页内容来源网络,仅供用户参考;我单位不保证亦不表示资料全面及准确无误,也不保证亦不表示这些资料为最新信息,如因任何原因,本网内容或者用户因倚赖本网内容造成任何损失或损害,我单位将不会负任何法律责任。如涉及版权问题,请提交至online#300.cn邮箱联系删除。

相关文章