C# 不同方式调用函数的性能对比

案例

using System;

using System.Diagnostics;

using System.Reflection;

using System.Reflection.Emit;

using System.Runtime.CompilerServices;



public class CallTest

{

    public delegate int AddDelegate(int x);



    public interface IAdd

    {

        int add(int i);

    }



    public class addClass : IAdd

    {

        [MethodImpl(MethodImplOptions.NoInlining)]

        public int add(int i)

        {

            return i + 1;

        }



        [MethodImpl(MethodImplOptions.NoInlining)]

        public static int static_add(int x)

        {

            return x + 1;

        }

    }



    public static MethodInfo addMethodInfo()

    {

        AssemblyName asmName = new AssemblyName();

        asmName.Name = "DynamicAssembly";

        AssemblyBuilder asmBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, AssemblyBuilderAccess.Run);

        ModuleBuilder modBuilder = asmBuilder.DefineDynamicModule("DynamicModule");

        MethodBuilder funBuilder = modBuilder.DefineGlobalMethod("add", MethodAttributes.Public
 | MethodAttributes.Static, typeof(int), new Type[1] { typeof(int) });

        ILGenerator il = funBuilder.GetILGenerator();



        il.Emit(OpCodes.Ldarg_0);

        il.Emit(OpCodes.Ldc_I4_1);

        il.Emit(OpCodes.Add);

        il.Emit(OpCodes.Ret);



        modBuilder.CreateGlobalFunctions();

        MethodInfo method = modBuilder.GetMethod("add");

        return method;

    }



    public static DynamicMethod addDynamicMethod()

    {

        DynamicMethod dm = new DynamicMethod("add", typeof(int), new Type[] { typeof(int) });

        ILGenerator il = dm.GetILGenerator();

        il.Emit(OpCodes.Ldarg_0);

        il.Emit(OpCodes.Ldc_I4_1);

        il.Emit(OpCodes.Add);

        il.Emit(OpCodes.Ret);

        return dm;

    }



    public static IAdd addInterface()

    {

        Type baseType = typeof(IAdd);



        //创建动态程序集。   

        AssemblyName asmName = new AssemblyName("add.assembly");

        AssemblyBuilder assembly = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, AssemblyBuilderAccess.Run);



        //创建动态模块。   

        ModuleBuilder module = assembly.DefineDynamicModule("add.module");



        //创建类型 MyClass。   

        TypeBuilder type = module.DefineType("MyClass", TypeAttributes.Class, typeof(Object), new Type[] { baseType });



        //创建方法   

        MethodAttributes attribute = baseType.GetMethod("add").Attributes & ~(MethodAttributes.Abstract);

        MethodBuilder method = type.DefineMethod("add", attribute, typeof(int), new Type[1] { typeof(int) });



        ILGenerator il = method.GetILGenerator();

        il = method.GetILGenerator();

        il.Emit(OpCodes.Ldarg_1);

        il.Emit(OpCodes.Ldc_I4_1);

        il.Emit(OpCodes.Add);

        il.Emit(OpCodes.Ret);



        // 显式接口方法需要定义 Override,而普通实现不需要。   

        type.DefineMethodOverride(method, baseType.GetMethod("add"));



        // 创建类型 MyClass。   

        Type myClass = type.CreateType();

        object o = Activator.CreateInstance(myClass);

        IAdd iadd = o as IAdd;

        return iadd;

    }



    static void Main(string[] args)

    {

        const int TIMES = 100000000;



        Stopwatch time = new Stopwatch();



        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES; )

            i++;

        time.Stop();

        Console.WriteLine("直接执行时间:" + time.ElapsedMilliseconds);



        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES; )

            i = addClass.static_add(i);

        time.Stop();

        Console.WriteLine("静态函数执行时间:" + time.ElapsedMilliseconds);



        time.Reset();

        time.Start();

        addClass add = new addClass();

        for (int i = 0; i < TIMES; )

            i = add.add(i);

        time.Stop();

        Console.WriteLine("成员函数执行时间:" + time.ElapsedMilliseconds);



        AddDelegate staticAddDelegate = new AddDelegate(addClass.static_add);

        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES; )

            i = staticAddDelegate(i);

        time.Stop();

        Console.WriteLine("静态方法的delegate执行时间:" + time.ElapsedMilliseconds);



        time.Reset();

        time.Start();

        IAdd iadd = new addClass();

        for (int i = 0; i < TIMES; )

            i = iadd.add(i);

        time.Stop();

        Console.WriteLine("接口函数执行时间:" + time.ElapsedMilliseconds);



        MethodInfo addMethod = addMethodInfo();

        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES / 100; )

            i = (int)addMethod.Invoke(null, new object[1] { i });

        time.Stop();

        Console.WriteLine("反射Invoke执行时间:" + time.ElapsedMilliseconds * 100);



        DynamicMethod dynamicMethod = addDynamicMethod();

        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES / 100; )

            i = (int)dynamicMethod.Invoke(null, new object[1] { i });

        time.Stop();

        Console.WriteLine("DynamicMethod.Invoke执行时间:" + time.ElapsedMilliseconds * 100);



        AddDelegate dynamicAddDelegate = (AddDelegate)dynamicMethod.CreateDelegate(typeof(AddDelegate));

        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES; )

            i = dynamicAddDelegate(i);

        time.Stop();

        Console.WriteLine("DynamicMethod生成delegate执行时间:" + time.ElapsedMilliseconds);



        IAdd dynamicIAdd = addInterface();

        time.Reset();

        time.Start();

        for (int i = 0; i < TIMES; )

            i = dynamicIAdd.add(i);

        time.Stop();

        Console.WriteLine("emit生成的interface执行时间:" + time.ElapsedMilliseconds);



        Console.ReadLine();

    }

}

.

直接执行时间:95
静态函数执行时间:388
成员函数执行时间:485
静态方法的delegate执行时间:728
接口函数执行时间:591
反射Invoke执行时间:259600
DynamicMethod.Invoke执行时间:600300
DynamicMethod生成delegate执行时间:623
emit生成的interface执行时间:621

 

.

此条目发表在article分类目录,贴了标签。将固定链接加入收藏夹。