注意Activator.CreateInstance两个重载方法的性能

今天扩展一个Type的扩展方法New:性能

        public static object New(this Type type, params object[] args)
        {
            Guard.ArgumentNull(type, "type");
            return Activator.CreateInstance(type, args);
        }

而后想到了测试一下其性能,因此就和直接使用Activator.CreateInstance方法做一下比较:测试

        public void TestCreateInstance()
        {
            Console.WriteLine(TimeWatcher.Watch(() =>
                {
                    for (var i = 0; i < 10000; i++)
                    {
                        var o = Activator.CreateInstance(typeof(TestSerializeClass1));
                    }
                }));
            Console.WriteLine(TimeWatcher.Watch(() =>
            {
                for (var i = 0; i < 10000; i++)
                {
                    var o = typeof(TestSerializeClass1).New();
                }
            }));
        }

这彷佛是画蛇添足的无用测试,却着实使我大吃一惊!this

00:00:00.0015076
00:00:00.0104130
 
为何发生了如此大的变化,不就是没有指定第二个参数么!!
使用Reflector查看 Activator.CreateInstance(Type type) 和  Activator.CreateInstance(Type type, params object[] args) 方法,发现它们的实现都不同,但具体慢在什么地方,暂时尚未时间去分析。
所以,在写公共类库的时候,性能测试是必须的,尤为是使用反射的状况下,更是要注意这样的陷阱。
 
修改后的New方法以下:
        public static object New(this Type type, params object[] args)
        {
            Guard.ArgumentNull(type, "type");
            if (args == null || args.Length == 0)
            {
                return Activator.CreateInstance(type);
            }

            return Activator.CreateInstance(type, args);
        }

再次测试的时间以下:spa

00:00:00.0016531
00:00:00.0020176
 
但仍是有一点点的影响,不过比起以前已经能够忽略不计了。
相关文章
相关标签/搜索