In einigen Fällen müssen wir Java -Code dynamisch generieren, dynamisch kompilieren und dann den Code ausführen. Javaapi bietet entsprechende Tools (Javacompiler) zur Implementierung der dynamischen Kompilierung. Im Folgenden stellen wir vor, wie Sie die dynamische Zusammenstellung von Java -Code über Javacompiler implementieren.
1. Holen Sie sich Javacompiler
Javacompiler Compiler = ToolProvider.getSystemJavacompiler ();
Holen Sie sich den von JDK zur Verfügung gestellten Java -Compiler, und wenn kein Compiler bereitgestellt wird, kehren Sie NULL zurück.
2. Zusammenstellung
// Holen Sie sich die Java -Dateiverwaltungsklasse Standardjavafilemanager Manager = Compiler.getStandardFilemanager (NULL, NULL, NULL); // Holen Sie sich die Iteratorin des Java -Datei -Objekts iterable <? erweitert javafileObject> iT = Manager.getjavafileObjects (Dateien); // Setzen Sie die Kompilierungsparameter ArrayList <string> ops = new ArrayList <string> (); Ops.Add ("-XLINT: UNCRECTED"); // CLASSPATHHOPs.Add ("-Classpath); Task = compiler.gettask (Null, Manager, Null, OPS, NULL, IT); // Compilation Task.call () ausführen;Wenn wir uns auf einen anderen Code in dem Quellcode verweisen, den wir kompilieren möchten, müssen wir den Referenzcodepfad auf -ClassPath festlegen, andernfalls schlägt die Kompilierung fehl.
III. Ausführung
// Der klassenname, der geladen werden soll, classname = "xxx.xxx.xxx"; // Die Klasse Loader Classloader Classloader = xxx.class.getClassloader (); // Laden Sie die Klasse Class <?> Cls = classLoader.loadClass (className); // Aufruf des Methode -Namens -Verfahrens von Methode, der Methode -Name -Markethuge "Achsenname"; {...}; // Erhalten Sie die Methodenmethode = cls.getDeclaredMethod (methodName, paramcls); // Erstellen Sie das Klasseninstanzobjekt obj = Cls.NewinStance (); // Methode Parameter Objekt [] params = {...}; // Methode Objekt Ergebnis = method.invoke (OBJ, Params);4. CODE CODE
//Classutil.javaimport java.io.fileWriter; import Java.io.BufferedWriter; Import Java.io.file; Import Java.io.ioException; Import Java.util.ArrayList; Importion Javax.tools.javacompiler; javax.tools.Standardjavafilemanager; import org.apache.commons.logging.log; import org.apache.commons.logging.logfactory; ToolProvider.getSystemjavacompiler ();}/** * den Java -Dateipfad * @param Datei * @return */private statische String getFilePath (String -Datei) {int last1 = Datei.lastindexof ('/'); int2 = Datei.lastIndexof ('//'). last1> last2? null); iterable <? erweitert javafileObject> iT = Manager.getJavafileObjects (Dateien); javacompiler.comPilationTask Task = Compiler.gettask (Null, Manager, Null, Ops, null, it); task.call (); if (logger.isdebugenable ()) {for (für (für (String)). Datei);}} catch (Ausnahme e) {logger.Error (e);} endlich {if (Manager! writeJavafile (String -Datei, String Quelle) löst die Ausnahme aus {if (logger.isdebugenabled ()) {logger.debug ("Java -Quellcode schreiben zu:"+file);} bufferedWriter bw = null; try {Datei -Datei (GetFilePath (); Filewriter (Datei)); bw.write (Quelle); bw.flush ();} catch (Ausnahme E) {throw e;} endlich {if (bw! null; try {classloader = classUtil.class.getClassloader (); cls = classloader.loadClass (Name); if (logger.isdebugenabled ()) {logger.debug ("Load class ["+name+"] von"+classloader);}} catch (AUSSCHLUSS E) {{{logger. Laden Sie die Klasse* @param filepath java code path* @param source java code* @param clsname class name* @param ops kompile parameter* @return*/public static class <?> loadClass (String filepath, String Quelle, String clsname, List <string> ops) {try try try try {writeJavaFile(CLASS_PATH+filePath,source);javac(ops,CLASS_PATH+filePath);return load(clsName);}catch (Exception e) {logger.error(e);}return null;}/** * Call class method* @param cls class* @param methodName method name* @param paramsCls method parameter type* @param params method parameter* @return */public static Object Invoke (Klasse <?> cls, String methodName, class <?> [] paramscls, Objekt [] Params) {Object result = null; try {method method = cls.getDeclaredMethod (methodname, paramscls); {Logger.Error (e);} Rückgabeergebnis;}}V. Test
public class classutiltest {private statische endgültige log -logger = logfactory.getLog (classutiltest.class); public static void main (String args []) {StringBuilder SB = new StringBuilder (); java.text.decimalformat;/n "); sb.append (" öffentliche Klasse sum {/n "); (30*data.get (/"f1/") + 20*data.get (/"f2/") + 50*data.get (/"f3/")/100;/n "); ArrayList <String> (); ops.add ("-xLint: Unkontrolliert"); // Die Code und return Classclass <?> Cls = classUtil.loadClass ("/com/sogar/test/sum.java", sb.toString (), "com.even.test.sum.sum", OPS); HashMap <String, double> (); Data.put ("F1", 10.0); Data.put ("F2", 20.0); Data.put ("F3", 30.0); // Führen Sie das Testmethode -Objekt Ergebnis = classutil.invoke (cls, "calculate", New Class [] {] map.class}, Neues Objekt [] {] {Data {Data} aus. Logger.debug (Daten); logger.debug ("(30*F1+20*F2+50*F3)/100 ="+Ergebnis);}Testergebnisse
16:12:02.860 DEBUG com.even.tools.ClassUtil - Write Java Source Code to: .../classes//com/even/test/Sum.java16:12:03.544 DEBUG com.even.tools.ClassUtil - Compile Java File:.../classes//com/even/test/Sum.java16:12:03.545 DEBUG com.even.tools.ClassUtil - Load Class[com.even.test.Sum] by sun.misc.Launcher$AppClassLoader@73d16e9316:12:03.547 DEBUG com.even.test.ClassUtilTest - {f1=10.0, f2=20.0, f3=30.0}16:12:03.547 DEBUG com.even.test.classutiltest - (30*f1+20*f2+50*f3)/100 = 22.0Zusammenfassen
Im obigen dreht sich alles um Java Dynamic Compilation- und Ausführungscode -Beispiele. Ich hoffe, es wird für alle hilfreich sein. Interessierte Freunde können weiterhin auf diese Seite verweisen:
Java -Programmierung dynamisch kompilierte und geladene Codefreigabe
Java Dynamic Programming bearbeiten Distanzproblem Beispielcode
Detaillierte Erläuterung der Implementierung von Referenzen und dynamischen Proxy in Java
Wenn es Mängel gibt, hinterlassen Sie bitte eine Nachricht, um darauf hinzuweisen. Vielen Dank an Freunde für Ihre Unterstützung für diese Seite!