zoukankan      html  css  js  c++  java
  • 反射(Reflection)的性能分析

    记得老早以前就看到有人把反射称之为“性能杀手",正好目前正在做的erp系统为了实现扩展,系统就是架构在反射的基础之上,数据交互也都是通过反射来实现。首先系统会产生太多dll,现在刚刚起步,已经高达43个之多,由于erp系统具有很复杂的业务功能,产品在发布阶段很可能产生200甚至更多的dll,且不说这几百个项目在调试的时候,漫长的等待是多么的痛苦,在产品推出去之后,这么多的dll的版本如何维护?多现在为止,除了windows还没有见过dll超过百的系统,难道我们的系统真的比windows还要难?这些暂且不提,先测试一下反射在系统应用的性能情况,测试程序如下:

    //被测试类
    using System;
    using System.Collections.Generic;
    using System.Text;

    namespace ClassLibrary1
    {
        
    public class CTester
        
    {
            
    public CTester()
            
    {
                a 
    = 10;
            }



            
    public void test1()
            
    {
                a 
    = (a - 0.0001* 1.0001;
            }

            
    private double a;
            
    public double geta() return a; }
        }

    }



    ///测试类
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Reflection;
    using System.Collections;

    namespace ConsoleApplication2
    {
       
            
    public class CTester
            
    {
                
    public CTester()
                
    {
                    a 
    = 10;
                }

            

                
    public void test1()
                
    {
                    a 
    = (a - 0.0001* 1.0001;
                }

                
    private double a;
                
    public double geta() return a; }
            }


       


        
    class Program
        
    {
            
    private string test1()
            
    {
                
    int now = System.Environment.TickCount;
               
                
    for (int i = 0; i < 1000; i++)
                
    {
                    
    for (int j = 0; j < 100; j++)
                    
    {
                        CTester aTest 
    = new CTester();
                        aTest.test1();
                        
                    }

                }


                
    string time = (System.Environment.TickCount - now).ToString();
                
    return time;
            }

            
    static Hashtable table = new Hashtable();
            
    private string test3()
            
    {
                
    int now = System.Environment.TickCount;
               
                
    for (int i = 0; i < 1000; i++)
                
    {
                    
    for (int j = 0; j < 100; j++)
                    
    {
                        Type theTest 
    = null;
                        
    if (table.ContainsKey("ConsoleApplication2.CTester"))
                        
    {
                            theTest 
    = table["ConsoleApplication2.CTester"as Type;
                        }

                        
    else
                        
    {
                            theTest 
    = Type.GetType("ConsoleApplication2.CTester");
                            table.Add(
    "ConsoleApplication2.CTester", theTest);
                        }

                        ConsoleApplication2.CTester theobj 
    = theTest.InvokeMember(null, BindingFlags.CreateInstance
                            , 
    nullnullnullas ConsoleApplication2.CTester;
                        theobj.test1();
                    }

                }


                
    string  time =(System.Environment.TickCount - now).ToString();
                
    return  time;
            }

            
    private string test2()
            
    {
                
    int now = System.Environment.TickCount;
                
    for (int i = 0; i < 1000; i++)
                
    {
                    
    for (int j = 0; j < 100; j++)
                    
    {
                        Type theTest 
    = theTest = Type.GetType("ConsoleApplication2.CTester"); ;
                        ConsoleApplication2.CTester theobj 
    = theTest.InvokeMember(null, BindingFlags.CreateInstance
                            , 
    nullnullnullas ConsoleApplication2.CTester;
                        theobj.test1();
                    }

                }


                
    string  time =(System.Environment.TickCount - now).ToString();
                
    return time;
            }

              
    static object InvokeMehod(string FileName,
                
    string MethodName,
                
    object[] Args)
            
    {
                Assembly a 
    = Assembly.LoadFrom(FileName);


                MethodInfo method 
    = null;
                Type HereType 
    = null;
                
    foreach (Module m in a.GetModules())
                
    {
                    
    foreach (Type t in m.GetTypes())
                    
    {

                        
    foreach (MethodInfo mInfo in t.GetMethods())
                        
    {
                            
    if (mInfo.Name == MethodName)
                            
    {
                                ParameterInfo[] pInfo 
    = mInfo.GetParameters();
                                
    if (pInfo.Length == Args.Length)
                                
    {
                                    
    bool same = true;
                                    
    for (int i = 0; i < pInfo.Length; i++)
                                    
    {
                                        
    if (Args[i] != null && pInfo[i].ParameterType != typeof(object)
                                            
    && pInfo[i].ParameterType != typeof(object[]))
                                        
    {
                                            
    if (pInfo[i].ParameterType != Args[i].GetType())
                                            
    {
                                                same 
    = false;
                                            }

                                        }

                                    }

                                    
    if (same)
                                    
    {
                                        HereType 
    = t;
                                        method 
    = mInfo;
                                    }

                                }

                            }


                            
    if (method != null)
                            
    {
                                
    break;
                            }

                        }


                        
    if (method != null)
                        
    {
                            
    break;
                        }

                    }


                    
    if (method != null)
                    
    {
                        
    break;
                    }

                }


                
    if (method == null)
                
    {
                    
    //Log.LogException(typeof(Excute), "没有发现:" + FileName + "/" + MethodName, new Exception("没有发现:" + FileName + "/" + MethodName));
                    return null;
                }


                
    object ins = null;
                
    if (!method.IsStatic)
                
    {
                    ins 
    = a.CreateInstance(HereType.FullName);
                }

                
    object RetObject = method.Invoke(ins, Args);
                
    return RetObject;
            }

        

            
    private string test5()
            
    {
                
    int now = System.Environment.TickCount;
                
    for (int i = 0; i < 1000; i++)
                
    {
                    
    for (int j = 0; j < 100; j++)
                    
    {
                        InvokeMehod(
    @"D:\ConsoleApplication2\ConsoleApplication2\ConsoleApplication2\bin\Debug\ClassLibrary1.dll""test1"new object[] { });
                    }

                }


                
    string time = (System.Environment.TickCount - now).ToString();
                
    return time;
            }

            
    static void Main(string[] args)
            
    {
                Program p 
    = new Program();
                
    string ticks = p.test1();
                Console.WriteLine(
    "用编译器执行:"+ticks);
                
    string t = p.test2();
                Console.WriteLine(
    "用反射执行"+t);
                
    string t1 = p.test3();
                Console.WriteLine(
    "优化之后的反射:"+t1);
                
    string t2 = p.test5();
                Console.WriteLine(
    "加载程序集并反射:"+t2);
                
    if (ticks.ToString() == "0")
                
    {
                    Console.WriteLine(
    "反射/编译: 不在一个级别上面");
                }

                
    else
                
    {
                    Console.WriteLine(
    "反射/编译 =" + (Convert.ToInt32(t) / Convert.ToInt32(ticks)).ToString());
                }

         
                
    if (ticks.ToString() == "0")
                
    {
                    Console.WriteLine(
    "加载程序集并反射/编译: 不在一个级别上面");
                }

                
    else
                
    {
                    Console.WriteLine(
    "加载程序集并反射/编译 =" + (Convert.ToInt32(t2) / Convert.ToInt32(ticks)).ToString());
                }

               

                Console.WriteLine(
    "加载程序集并反射/反射 =" + (Convert.ToInt32(t2) / Convert.ToInt32(t)).ToString());
               
                Console.Read();
            }

        }

    }

    测试结果为:

    638倍的性能损失,不知道算大算小,反正项目经理说无所谓。
    赫赫,无(。。)者无畏

  • 相关阅读:
    elk 之elasticsearch 部分参数参考(1)
    ubuntu16.04安装mariadb 缺少ncurses-devel
    死锁以及避免死锁
    python中的@
    Python中的logging模块
    Cannot find /usr/src/jdk1.7.0_79/lib/*.*/bin/setclasspath.sh 找不到文件
    shelve -- 用来持久化任意的Python对象
    Python-机器学习基础-K近邻算法
    Python-机器学习基础-Pandas
    Java-多线程
  • 原文地址:https://www.cnblogs.com/jillzhang/p/473326.html
Copyright © 2011-2022 走看看