| 两个C#动态编译代码的例子 |
| [ 作者:佚名 转贴自:网络转载 阅读次数:34 更新时间:2007-8-27 11:39:00 录入:刘光勇 ] |
|
|
|
动态生成代码程序收集NO1:
using System; using System.Collections.Generic; using System.Reflection; using System.Text; using System.CodeDom; using System.CodeDom.Compiler;
namespace csrepl { class Program {
static string funcprefix = "using System; " + "public delegate void Proc(); " + "public class Wrapper { " + " public static object Set(string name, object value) { " + " AppDomain.CurrentDomain.SetData(name, value); " + " return value; " + " } " + " public static object Get(string name) { " + " return AppDomain.CurrentDomain.GetData(name); " + " } " + " public static object Invoke(Proc proc) { " + " proc(); " + " return null; " + " } " + " public static object Eval() { return "; static string funcsuffix = "; } }";
static string StringEval(string expr) { string program = funcprefix + expr + funcsuffix;
ICodeCompiler compiler = CodeDomProvider.CreateProvider("C#").CreateCompiler(); CompilerParameters cp = new CompilerParameters(); cp.GenerateExecutable = false; cp.GenerateInMemory = true;
CompilerResults results = compiler.CompileAssemblyFromSource(cp, program); if (results.Errors.HasErrors) { if (results.Errors[0].ErrorNumber == "CS0029") return StringEval("Invoke(delegate { " + expr + "; })"); return results.Errors[0].ErrorText; } else { Assembly assm = results.CompiledAssembly; Type target = assm.GetType("Wrapper"); MethodInfo method = target.GetMethod("Eval"); object result = method.Invoke(null, null); return result == null ? null : result.ToString(); } }
static void Main(string[] args) {
while (true ) { Console.Write("> "); Console.Out.Flush(); string expr = Console.ReadLine(); if (expr == null) break; try { string result = StringEval(expr); Console.WriteLine(result); } catch (TargetInvocationException ex) { Console.WriteLine(ex.InnerException.GetType().Name + ": " + ex.InnerException.Message); } catch (Exception ex) { Console.WriteLine(ex.GetType().Name + ": " + ex.Message); } }
} } }
代码2:
private void Compiler(string code) { CompilerParameters vCompilerParameters = new CompilerParameters(); vCompilerParameters.GenerateExecutable = false; vCompilerParameters.GenerateInMemory = true; vCompilerParameters.ReferencedAssemblies.Add("System.Windows.Forms.dll"); string vSource = "using System.Windows.Forms;\n" + "public class Temp\n" + "{\n" + " public void Test()\n" + " {\n" + " " + code + "\n" + " }\n" + "}\n"; CompilerResults vCompilerResults = CodeDomProvider.CreateProvider("CSharp").CompileAssemblyFromSource(vCompilerParameters, vSource);
Assembly vAssembly = vCompilerResults.CompiledAssembly; object vTemp = vAssembly.CreateInstance("Temp"); MethodInfo vTest = vTemp.GetType().GetMethod("Test"); vTest.Invoke(vTemp, null); }
string code = "int sum = 0;\nfor(int i = 0; i < 100; i++)\n{\nsum += i;\n}\nMessageBox.Show(sum.ToString());"; Compiler(code);
|
|
|
|