从字符串构建DoWorkEventHandler
本文关键字:DoWorkEventHandler 构建 字符串 | 更新日期: 2023-09-27 17:59:23
我有一个Actions列表。
public class Action {
public string Name { get; set; }
public DoWorkEventHandler DoWork{ get; set; }
}
这是在代码中填充的。
list.Add(new Action("Name", SomeRandomMethod));
...
当有人从该列表中选择一个操作时,它将执行相应的操作。
private void ListBoxSelectionChanged(object sender, SelectionChangedEventArgs e) {
var item = (Action) ListBoxScripts.SelectedItem;
BackgroundWorker worker = new BackgroundWorker();
worker.DoWork += item.DoWork;
worker.RunWorkerAsync();
}
但是我想从数据库中定义和构建这个列表。那么,当我从DB中得到的是一个带有方法名的字符串时,我应该如何创建一个带有DoWorkEventHandler参数的Action?
有很多方法可以做到这一点。
您可以声明一个包含允许调用的所有方法名称的enum
,然后在启动时使用反射构建一个将enums
映射到methodinfo
的字典。您可以将枚举存储在数据库中。
另一种选择是将类/方法装饰如下:
[ContainsScriptableMethod("MyClassIdentifyingName"] // or a number
class MyUserScriptableMethods
{
[ScriptableMethod("MyMethodIdentifyingName")] // Or just a number as an identifier
void MyMethod()
{
// Do non-malicious stuff.
}
}
在查找要调用的方法时,您可以从数据库中获取类ID,然后使用反射来获取具有正确ID的[ContainsScriptableMethod]
属性的所有类,然后对查找方法执行同样的操作。
如果只有少数定义的类具有可以调用/脚本化的方法,则可以只为该方法提供一个属性。
下面的示例代码:
// Enumerate all classes with the ContainsScriptableMethod like so
foreach(var ClassWithAttribute in GetTypesWithAttribute(Assembly.GetExecutingAssembly(), typeof(ContainsScriptableMethodAttribute))
{
// Loop through each method in the class with the attribute
foreach(var MethodWithAttribute in GetMethodsWithAttribute(ClassWithAttribute, ScriptableMethodAttribute))
{
// You now have information about a method that can be called. Use Attribute.GetCustomAttribute to get the ID of this method, then add it to a dictionary, or invoke it directly.
}
}
static IEnumerable<Type> GetTypesWithAttribute(Assembly assembly, Type AttributeType)
{
foreach(Type type in assembly.GetTypes())
{
if (type.GetCustomAttributes(AttributeType, true).Length > 0)
{
yield return type;
}
}
}
static IEnumerable<MethodInfo> GetMethodsWithAttribute(Type ClassType, Type AttributeType)
{
foreach(var Method in ClassType.GetMethods())
{
if (Attribute.GetCustomAttribute(AttributeType) != null)
{
yield Method;
}
}
}