是否可以在 C# 中编写一个简单快速的函数来执行字符串中的任意方法?例如,如果我设置 MyString="MessageBox.Show("Some Message")" 然后调用 ExecuteString(MyString),则会弹出一个消息框,其中包含“Some Message”。
(我可能在上面的代码中犯了某种错误。我还不知道 C#;我正在尝试评估它是否适合特定项目。)
是否可以在 C# 中编写一个简单快速的函数来执行字符串中的任意方法?例如,如果我设置 MyString="MessageBox.Show("Some Message")" 然后调用 ExecuteString(MyString),则会弹出一个消息框,其中包含“Some Message”。
(我可能在上面的代码中犯了某种错误。我还不知道 C#;我正在尝试评估它是否适合特定项目。)
您应该能够使用它并将运行字符串所需的代码包装到函数中。
本质上,您所做的是将一小部分 C# 代码包装在Program.Main
样式函数中,引用一些程序集以获得基本功能(可能包括您自己的程序集),然后在内存中运行已编译的程序。
请注意,这可能比您只需运行一两行代码所需的开销更大。
您似乎正在寻找的是CS-Script
唉,C# 不是那种动态语言。您不能轻易做到这一点,如果您确实需要这样做,请考虑使用更符合您需求的 .Net 语言,例如 IronPython 或 IronRuby。
您最好的替代方法是使用 CodeDom 命名空间,因为来自此论坛主题的这个真正令人费解且令人发指的示例显示:
using System;
using System.CodeDom;
using System.CodeDom.Compiler;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Text;
using System.Windows.Forms;
namespace TestApp
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
SampleLib.SampleType test = new SampleLib.SampleType();
private void button1_Click(object sender, EventArgs e)
{
// Dynamically build and call the method
label1.Text = test.MyText;
}
private void button2_Click(object sender, EventArgs e)
{
StringBuilder DynamicCode = new StringBuilder();
DynamicCode.Append("namespace TestDynamic");
DynamicCode.Append("{");
DynamicCode.Append("public class DynamicCode");
DynamicCode.Append("{");
DynamicCode.Append("public static void EditText(SampleLib.SampleType t)");
DynamicCode.Append("{");
DynamicCode.Append("t.MyText = \"Goodbye!\";");
DynamicCode.Append("}");
DynamicCode.Append("}");
DynamicCode.Append("}");
string CodeString = DynamicCode.ToString();
System.IO.FileInfo fi = new System.IO.FileInfo(Application.ExecutablePath);
CodeDomProvider provider = CodeDomProvider.CreateProvider("C#");
CompilerParameters CompileParams = new CompilerParameters(new string[] { fi.DirectoryName + "\\SampleLib.dll" },
fi.DirectoryName + "\\Dynamic.dll");
CompileParams.MainClass = "DynamicCode";
CompileParams.GenerateExecutable = false;
//CompileParams.GenerateInMemory = true;
CompilerResults r = provider.CompileAssemblyFromSource(CompileParams, new string[] {CodeString});
foreach (CompilerError er in r.Errors)
{
Console.WriteLine(er.ErrorText);
}
}
private void button3_Click(object sender, EventArgs e)
{
// Dynamically call assembly
System.IO.FileInfo fi = new System.IO.FileInfo(Application.ExecutablePath);
Assembly dynAsm = Assembly.LoadFile(fi.DirectoryName + "\\Dynamic.dll");
if (dynAsm != null)
{
object o = dynAsm.CreateInstance("TestDynamic.DynamicCode", true);
Type t = dynAsm.GetType("TestDynamic.DynamicCode");
t.GetMethod("EditText").Invoke(o, new object[]{test});
}
}
}
}