通过将函数名称作为字符串传递来动态调用任何函数

Jos*_*osh 25 c# reflection function instance

如何自动创建实例并动态执行其功能的过程?

谢谢

编辑:需要一个传递参数的选项.谢谢

Jon*_*eet 47

您是否只想调用无参数构造函数来创建实例?类型是否也被指定为字符串,或者您可以将其作为通用方法吗?例如:

// All error checking omitted. In particular, check the results
// of Type.GetType, and make sure you call it with a fully qualified
// type name, including the assembly if it's not in mscorlib or
// the current assembly. The method has to be a public instance
// method with no parameters. (Use BindingFlags with GetMethod
// to change this.)
public void Invoke(string typeName, string methodName)
{
    Type type = Type.GetType(typeName);
    object instance = Activator.CreateInstance(type);
    MethodInfo method = type.GetMethod(methodName);
    method.Invoke(instance, null);
}
Run Code Online (Sandbox Code Playgroud)

要么

public void Invoke<T>(string methodName) where T : new()
{
    T instance = new T();
    MethodInfo method = typeof(T).GetMethod(methodName);
    method.Invoke(instance, null);
}
Run Code Online (Sandbox Code Playgroud)


Nad*_*zie 20

要调用构造函数,Activator.CreateInstance将完成这一操作.它有一堆重载让你的生活更轻松.

如果您的构造函数是无参数的:

object instance = Activator.CreateInstance(type)
Run Code Online (Sandbox Code Playgroud)

如果您需要参数:

object instance =  Activator.CreateInstance(type, param1, param2)
Run Code Online (Sandbox Code Playgroud)

要调用一个方法,一旦你有了Type对象,就可以调用它GetMethod来获取方法,然后Invoke(带或不带参数)来调用它.如果需要它,Invoke还会给你正在调用的函数的返回值(如果是void方法,则返回null),

有关更详细的示例(粘贴到控制台应用程序中并继续):

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Reflection;

namespace Test
{
    public static class Invoker
    {
        public static object CreateAndInvoke(string typeName, object[] constructorArgs, string methodName, object[] methodArgs)
        {
            Type type = Type.GetType(typeName);
            object instance = Activator.CreateInstance(type, constructorArgs);

            MethodInfo method = type.GetMethod(methodName);
            return method.Invoke(instance, methodArgs);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            // Default constructor, void method
            Invoker.CreateAndInvoke("Test.Tester", null, "TestMethod", null);

            // Constructor that takes a parameter
            Invoker.CreateAndInvoke("Test.Tester", new[] { "constructorParam" }, "TestMethodUsingValueFromConstructorAndArgs", new object[] { "moo", false });

            // Constructor that takes a parameter, invokes a method with a return value
            string result = (string)Invoker.CreateAndInvoke("Test.Tester", new object[] { "constructorValue" }, "GetContstructorValue", null);
            Console.WriteLine("Expect [constructorValue], got:" + result);

            Console.ReadKey(true);
        }
    }

    public class Tester
    {
        public string _testField;

        public Tester()
        {
        }

        public Tester(string arg)
        {
            _testField = arg;
        }

        public void TestMethod()
        {
            Console.WriteLine("Called TestMethod");
        }

        public void TestMethodWithArg(string arg)
        {
            Console.WriteLine("Called TestMethodWithArg: " + arg);
        }

        public void TestMethodUsingValueFromConstructorAndArgs(string arg, bool arg2)
        {
            Console.WriteLine("Called TestMethodUsingValueFromConstructorAndArg " + arg + " " + arg2 + " " + _testField);
        }

        public string GetContstructorValue()
        {
            return _testField;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)


Fre*_*örk 7

假设您要调用的方法不带任何参数:

public void InvokeMethod(Type type, string methodName)
{
    object instance = Activator.CreateInstance(type);
    MethodInfo method = type.GetMethod(methodName, BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);

    method.Invoke(instance, null);
}
Run Code Online (Sandbox Code Playgroud)